Skip to content

Commit

Permalink
changed mixed_fs_limiter test to DG and DG1_equispaced
Browse files Browse the repository at this point in the history
  • Loading branch information
ta440 committed Nov 15, 2023
1 parent 18867a5 commit 021d9d7
Show file tree
Hide file tree
Showing 2 changed files with 32 additions and 56 deletions.
37 changes: 11 additions & 26 deletions gusto/limiters.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
"""

from firedrake import (BrokenElement, Function, FunctionSpace, interval,
FiniteElement, TensorProductElement, split)
FiniteElement, TensorProductElement)
from firedrake.slope_limiter.vertex_based_limiter import VertexBasedLimiter
from gusto.kernels import LimitMidpoints

Expand Down Expand Up @@ -184,44 +184,29 @@ class MixedFSLimiter(object):
"""An object to hold a dictionary that defines limiters for transported prognostic

Check failure on line 184 in gusto/limiters.py

View workflow job for this annotation

GitHub Actions / Run linter

W291

gusto/limiters.py:184:87: W291 trailing whitespace
variables. Different limiters may be applied to different fields and not every transported variable needs a defined limiter.
"""

def __init__(self, equation, sublimiters):
"""
Args:
equation (:class: 'PrognosticEquationSet'): the prognostic equation(s)
sublimiters (dict): A dictionary holding limiters defined for individual prognostic variables
sublimiters (dict): A dictionary holding limiters defined for individual prognostic variables
Raises:
ValueError: If a limiter is defined for a field that is not in the prognostic variable set
"""
self.sublimiters = sublimiters
for tracer, sublimiter in sublimiters.items():
# Check that the tracer is being solved in the equation:
if tracer not in equation.field_names:
raise ValueError(f"The limiter for {tracer} is for a field that does not exist in the equation set")

for field, sublimiter in sublimiters.items():
# Check that the field is in the prognostic variable set:
if field not in equation.field_names:
raise ValueError(f"The limiter defined for {field} is for a field that does not exist in the equation set")
else:
self.sublimiters[tracer].idx = equation.field_names.index(tracer)

#for tracer in tracers:
# if tracer.name in sublimiters:
# sublimiter = sublimiters.get(tracer.name)
# print(sublimiter)
# self.sublimiters[tracer.name].idx = equation.field_names.index(tracer.name

self.sublimiters[field].idx = equation.field_names.index(field)

def apply(self, fields):
"""
Apply the individual limiters to specific prognostic variables
"""

#for tracer in self.tracers:
# if tracer.name in self.sublimiters:
# sublimiter = self.sublimiters[tracer.name]
# field = fields.subfunctions[sublimiter.idx]
# sublimiter.apply(field)
# print(f'Applying sublimiter on {tracer.name} field')


for _, sublimiter in self.sublimiters.items():
field = fields.subfunctions[sublimiter.idx]
sublimiter.apply(field)
#print(f'Applying sublimiter on {tracer} field')

51 changes: 21 additions & 30 deletions integration-tests/transport/test_limiters.py
Original file line number Diff line number Diff line change
Expand Up @@ -53,8 +53,7 @@ def setup_limiters(dirname, space):
elif space == 'mixed_FS':
V = domain.spaces('HDiv')
VA = domain.spaces('DG')
#VB = domain.spaces('theta')
VB = domain.spaces('DG')
VB = domain.spaces('DG1_equispaced')
else:
raise NotImplementedError

Expand All @@ -65,10 +64,7 @@ def setup_limiters(dirname, space):
tracerA = ActiveTracer(name='tracerA', space='DG',
variable_type=TracerVariableType.mixing_ratio,
transport_eqn=TransportEquationType.advective)
#tracerB = ActiveTracer(name='tracerB', space='theta',
# variable_type=TracerVariableType.mixing_ratio,
# transport_eqn=TransportEquationType.advective)
tracerB = ActiveTracer(name='tracerB', space='DG',
tracerB = ActiveTracer(name='tracerB', space='DG1_equispaced',
variable_type=TracerVariableType.mixing_ratio,
transport_eqn=TransportEquationType.advective)
tracers = [tracerA, tracerB]
Expand Down Expand Up @@ -106,14 +102,9 @@ def setup_limiters(dirname, space):

elif space == 'mixed_FS':
sublimiters = {'tracerA': DG1Limiter(domain.spaces('DG')),
'tracerB': DG1Limiter(domain.spaces('DG'))}
#'tracerB': ThetaLimiter(domain.spaces('theta'))}
# Need Embedded DG if wanting to test theta limiter.
'tracerB': VertexBasedLimiter(domain.spaces('DG1_equispaced'))}
MixedLimiter = MixedFSLimiter(eqn, sublimiters)
transport_schemes = SSPRK3(domain, limiter=MixedLimiter)

#theta_opts = EmbeddedDGOptions()

else:
raise NotImplementedError

Expand Down Expand Up @@ -234,8 +225,8 @@ def setup_limiters(dirname, space):
return stepper, tmax, true_field

#move mixed_FS to the end once finished debugging
@pytest.mark.parametrize('space', ['Vtheta_degree_0', 'mixed_FS'])#, 'Vtheta_degree_1',
#'DG0', 'DG1', 'DG1_equispaced'])
@pytest.mark.parametrize('space', ['Vtheta_degree_0', 'Vtheta_degree_1', 'DG0',
'DG1', 'DG1_equispaced', 'mixed_FS'])
def test_limiters(tmpdir, space):

# Setup and run
Expand All @@ -245,50 +236,50 @@ def test_limiters(tmpdir, space):
stepper, tmax, true_fieldA, true_fieldB = setup_limiters(dirname, space)
else:
stepper, tmax, true_field = setup_limiters(dirname, space)

stepper.run(t=0, tmax=tmax)

tol = 1e-9

if space == 'mixed_FS':
final_fieldA = stepper.fields('tracerA')
final_fieldB = stepper.fields('tracerB')

# Check tracer is roughly in the correct place
assert norm(true_fieldA - final_fieldA) / norm(true_fieldA) < 0.05, \
'Something is wrong with the DG space tracer using a mixed limiter'

# Check tracer is roughly in the correct place
assert norm(true_fieldB - final_fieldB) / norm(true_fieldB) < 0.05, \
'Something is wrong with the theta space tracer using a mixed limiter'
'Something is wrong with the DG1 equispaced tracer using a mixed limiter'

# Check for no new overshoots in A
assert np.max(final_fieldA.dat.data) <= np.max(true_fieldA.dat.data) + tol, \
'Application of the DG space limiter in the mixed limiter has not prevented overshoots'

# Check for no new undershoots in A
assert np.min(final_fieldA.dat.data) >= np.min(true_fieldA.dat.data) - tol, \
'Application of the DG space limiter in the mixed limiter has not prevented undershoots'

# Check for no new overshoots in B
assert np.max(final_fieldB.dat.data) <= np.max(true_fieldB.dat.data) + tol, \
'Application of the theta space limiter in the mixed limiter has not prevented overshoots'
'Application of the DG1 equispaced limiter in the mixed limiter has not prevented overshoots'

# Check for no new undershoots in B
assert np.min(final_fieldB.dat.data) >= np.min(true_fieldB.dat.data) - tol, \
'Application of the theta space limiter in the mixed limiter has not prevented undershoots'
'Application of the DG1 equispaced limiter in the mixed limiter has not prevented undershoots'

else:
final_field = stepper.fields('tracer')

# Check tracer is roughly in the correct place
assert norm(true_field - final_field) / norm(true_field) < 0.05, \
'Something appears to have gone wrong with transport of tracer using a limiter'

# Check for no new overshoots
assert np.max(final_field.dat.data) <= np.max(true_field.dat.data) + tol, \
'Application of limiter has not prevented overshoots'

# Check for no new undershoots
assert np.min(final_field.dat.data) >= np.min(true_field.dat.data) - tol, \
'Application of limiter has not prevented undershoots'

0 comments on commit 021d9d7

Please sign in to comment.