Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
trixi-framework
GitHub Repository: trixi-framework/Trixi.jl
Path: blob/main/examples/structured_2d_dgsem/elixir_advection_coupled.jl
5586 views
1
using OrdinaryDiffEqLowStorageRK
2
using Trixi
3
4
###############################################################################
5
# Coupled semidiscretization of four linear advection systems using converter functions such that
6
# they are also coupled across the domain boundaries to generate a periodic system.
7
#
8
# In this elixir, we have a square domain that is divided into a upper-left, lower-left,
9
# upper-right and lower-right quarter. On each quarter
10
# of the domain, a completely independent SemidiscretizationHyperbolic is created for the
11
# linear advection equations. The four systems are coupled in the x and y-direction.
12
# For a high-level overview, see also the figure below:
13
#
14
# (-1, 1) ( 1, 1)
15
# ┌────────────────────┬────────────────────┐
16
# │ ↑ coupled ↑ │ ↑ coupled ↑ │
17
# │ │ │
18
# │ ========= │ ========= │
19
# │ system #1 │ system #2 │
20
# │ ========= │ ========= │
21
# │ │ │
22
# │<-- coupled │<-- coupled │
23
# │ coupled -->│ coupled -->│
24
# │ │ │
25
# │ ↓ coupled ↓ │ ↓ coupled ↓ │
26
# ├────────────────────┼────────────────────┤
27
# │ ↑ coupled ↑ │ ↑ coupled ↑ │
28
# │ │ │
29
# │ ========= │ ========= │
30
# │ system #3 │ system #4 │
31
# │ ========= │ ========= │
32
# │ │ │
33
# │<-- coupled │<-- coupled │
34
# │ coupled -->│ coupled -->│
35
# │ │ │
36
# │ ↓ coupled ↓ │ ↓ coupled ↓ │
37
# └────────────────────┴────────────────────┘
38
# (-1, -1) ( 1, -1)
39
40
advection_velocity = (0.2, -0.7)
41
equations = LinearScalarAdvectionEquation2D(advection_velocity)
42
43
# Create DG solver with polynomial degree = 3 and (local) Lax-Friedrichs/Rusanov flux as surface flux
44
solver = DGSEM(polydeg = 3, surface_flux = flux_lax_friedrichs)
45
46
# This will be the number of elements for each quarter/semidiscretization.
47
cells_per_dimension = (8, 8)
48
49
###########
50
# system #1
51
###########
52
53
coordinates_min1 = (-1.0, 0.0) # minimum coordinates (min(x), min(y))
54
coordinates_max1 = (0.0, 1.0) # maximum coordinates (max(x), max(y))
55
56
mesh1 = StructuredMesh(cells_per_dimension, coordinates_min1, coordinates_max1,
57
periodicity = false)
58
59
# Define the coupling functions
60
coupling_function12 = (x, u, equations_other, equations_own) -> u
61
coupling_function13 = (x, u, equations_other, equations_own) -> u
62
63
# Define the coupling boundary conditions and the system it is coupled to.
64
boundary_conditions_x_neg1 = BoundaryConditionCoupled(2, (:end, :i_forward), Float64,
65
coupling_function12)
66
boundary_conditions_x_pos1 = BoundaryConditionCoupled(2, (:begin, :i_forward), Float64,
67
coupling_function12)
68
boundary_conditions_y_neg1 = BoundaryConditionCoupled(3, (:i_forward, :end), Float64,
69
coupling_function13)
70
boundary_conditions_y_pos1 = BoundaryConditionCoupled(3, (:i_forward, :begin), Float64,
71
coupling_function13)
72
73
# A semidiscretization collects data structures and functions for the spatial discretization
74
semi1 = SemidiscretizationHyperbolic(mesh1, equations, initial_condition_convergence_test,
75
solver;
76
boundary_conditions = (;
77
x_neg = boundary_conditions_x_neg1,
78
x_pos = boundary_conditions_x_pos1,
79
y_neg = boundary_conditions_y_neg1,
80
y_pos = boundary_conditions_y_pos1))
81
82
###########
83
# system #2
84
###########
85
86
coordinates_min2 = (0.0, 0.0) # minimum coordinates (min(x), min(y))
87
coordinates_max2 = (1.0, 1.0) # maximum coordinates (max(x), max(y))
88
89
mesh2 = StructuredMesh(cells_per_dimension, coordinates_min2, coordinates_max2,
90
periodicity = false)
91
92
# Define the coupling functions
93
coupling_function21 = (x, u, equations_other, equations_own) -> u
94
coupling_function24 = (x, u, equations_other, equations_own) -> u
95
96
# Define the coupling boundary conditions and the system it is coupled to.
97
boundary_conditions_x_neg2 = BoundaryConditionCoupled(1, (:end, :i_forward), Float64,
98
coupling_function21)
99
boundary_conditions_x_pos2 = BoundaryConditionCoupled(1, (:begin, :i_forward), Float64,
100
coupling_function21)
101
boundary_conditions_y_neg2 = BoundaryConditionCoupled(4, (:i_forward, :end), Float64,
102
coupling_function24)
103
boundary_conditions_y_pos2 = BoundaryConditionCoupled(4, (:i_forward, :begin), Float64,
104
coupling_function24)
105
106
# A semidiscretization collects data structures and functions for the spatial discretization
107
semi2 = SemidiscretizationHyperbolic(mesh2, equations, initial_condition_convergence_test,
108
solver;
109
boundary_conditions = (;
110
x_neg = boundary_conditions_x_neg2,
111
x_pos = boundary_conditions_x_pos2,
112
y_neg = boundary_conditions_y_neg2,
113
y_pos = boundary_conditions_y_pos2))
114
115
###########
116
# system #3
117
###########
118
119
coordinates_min3 = (-1.0, -1.0) # minimum coordinates (min(x), min(y))
120
coordinates_max3 = (0.0, 0.0) # maximum coordinates (max(x), max(y))
121
122
mesh3 = StructuredMesh(cells_per_dimension, coordinates_min3, coordinates_max3,
123
periodicity = false)
124
125
# Define the coupling functions
126
coupling_function34 = (x, u, equations_other, equations_own) -> u
127
coupling_function31 = (x, u, equations_other, equations_own) -> u
128
129
# Define the coupling boundary conditions and the system it is coupled to.
130
boundary_conditions_x_neg3 = BoundaryConditionCoupled(4, (:end, :i_forward), Float64,
131
coupling_function34)
132
boundary_conditions_x_pos3 = BoundaryConditionCoupled(4, (:begin, :i_forward), Float64,
133
coupling_function34)
134
boundary_conditions_y_neg3 = BoundaryConditionCoupled(1, (:i_forward, :end), Float64,
135
coupling_function31)
136
boundary_conditions_y_pos3 = BoundaryConditionCoupled(1, (:i_forward, :begin), Float64,
137
coupling_function31)
138
139
# A semidiscretization collects data structures and functions for the spatial discretization
140
semi3 = SemidiscretizationHyperbolic(mesh3, equations, initial_condition_convergence_test,
141
solver;
142
boundary_conditions = (;
143
x_neg = boundary_conditions_x_neg3,
144
x_pos = boundary_conditions_x_pos3,
145
y_neg = boundary_conditions_y_neg3,
146
y_pos = boundary_conditions_y_pos3))
147
148
###########
149
# system #4
150
###########
151
152
coordinates_min4 = (0.0, -1.0) # minimum coordinates (min(x), min(y))
153
coordinates_max4 = (1.0, 0.0) # maximum coordinates (max(x), max(y))
154
155
mesh4 = StructuredMesh(cells_per_dimension, coordinates_min4, coordinates_max4,
156
periodicity = false)
157
158
# Define the coupling functions
159
coupling_function43 = (x, u, equations_other, equations_own) -> u
160
coupling_function42 = (x, u, equations_other, equations_own) -> u
161
162
# Define the coupling boundary conditions and the system it is coupled to.
163
boundary_conditions_x_neg4 = BoundaryConditionCoupled(3, (:end, :i_forward), Float64,
164
coupling_function43)
165
boundary_conditions_x_pos4 = BoundaryConditionCoupled(3, (:begin, :i_forward), Float64,
166
coupling_function43)
167
boundary_conditions_y_neg4 = BoundaryConditionCoupled(2, (:i_forward, :end), Float64,
168
coupling_function42)
169
boundary_conditions_y_pos4 = BoundaryConditionCoupled(2, (:i_forward, :begin), Float64,
170
coupling_function42)
171
172
# A semidiscretization collects data structures and functions for the spatial discretization
173
semi4 = SemidiscretizationHyperbolic(mesh4, equations, initial_condition_convergence_test,
174
solver;
175
boundary_conditions = (;
176
x_neg = boundary_conditions_x_neg4,
177
x_pos = boundary_conditions_x_pos4,
178
y_neg = boundary_conditions_y_neg4,
179
y_pos = boundary_conditions_y_pos4))
180
181
# Create a semidiscretization that bundles all the semidiscretizations.
182
semi = SemidiscretizationCoupled(semi1, semi2, semi3, semi4)
183
184
###############################################################################
185
# ODE solvers, callbacks etc.
186
187
# Create ODE problem with time span from 0.0 to 2.0
188
ode = semidiscretize(semi, (0.0, 2.0))
189
190
# At the beginning of the main loop, the SummaryCallback prints a summary of the simulation setup
191
# and resets the timers
192
summary_callback = SummaryCallback()
193
194
# The AnalysisCallback allows to analyse the solution in regular intervals and prints the results
195
analysis_callback1 = AnalysisCallback(semi1, interval = 100)
196
analysis_callback2 = AnalysisCallback(semi2, interval = 100)
197
analysis_callback3 = AnalysisCallback(semi3, interval = 100)
198
analysis_callback4 = AnalysisCallback(semi4, interval = 100)
199
analysis_callback = AnalysisCallbackCoupled(semi, analysis_callback1, analysis_callback2,
200
analysis_callback3, analysis_callback4)
201
202
# The SaveSolutionCallback allows to save the solution to a file in regular intervals
203
save_solution = SaveSolutionCallback(interval = 100,
204
solution_variables = cons2prim)
205
206
# The StepsizeCallback handles the re-calculation of the maximum Δt after each time step
207
stepsize_callback = StepsizeCallback(cfl = 1.6)
208
209
# Create a CallbackSet to collect all callbacks such that they can be passed to the ODE solver
210
callbacks = CallbackSet(summary_callback, analysis_callback, save_solution,
211
stepsize_callback)
212
213
###############################################################################
214
# run the simulation
215
216
# OrdinaryDiffEq's `solve` method evolves the solution in time and executes the passed callbacks
217
sol = solve(ode, CarpenterKennedy2N54(williamson_condition = false);
218
dt = 1.0, # solve needs some value here but it will be overwritten by the stepsize_callback
219
ode_default_options()..., callback = callbacks);
220
221