ViennaLS
Loading...
Searching...
No Matches
lsAdvectIntegrationSchemes.hpp
Go to the documentation of this file.
1#pragma once
2
4#include <lsDomain.hpp>
5
6namespace viennals {
7
24
25// Legacy naming (deprecated, will be removed in future versions)
26using IntegrationSchemeEnum [[deprecated("Use SpatialSchemeEnum instead")]] =
28
36
37// Forward declaration
38template <class T, int D> class Advect;
39} // namespace viennals
40
41namespace lsInternal {
42
43template <class T, int D> struct AdvectTimeIntegration {
45
46 static double evolveForwardEuler(AdvectType &kernel, double maxTimeStep) {
47 if (kernel.currentTimeStep < 0. || kernel.storedRates.empty())
48 kernel.computeRates(maxTimeStep);
49
50 kernel.updateLevelSet(kernel.currentTimeStep);
51
52 kernel.rebuildLS();
53
54 kernel.adjustLowerLayers();
55
56 return kernel.currentTimeStep;
57 }
58
59 static double evolveRungeKutta2(AdvectType &kernel, double maxTimeStep) {
60 // TVD Runge-Kutta 2nd Order (Heun's Method)
61 // 1. Determine time step
62 kernel.computeRates(maxTimeStep);
63 const double dt = kernel.getCurrentTimeStep();
64
65 // 2. Save u^n
66 if (kernel.originalLevelSet == nullptr) {
67 kernel.originalLevelSet =
68 viennals::Domain<T, D>::New(kernel.levelSets.back()->getGrid());
69 }
70 kernel.originalLevelSet->deepCopy(kernel.levelSets.back());
71
72 if (dt <= 0)
73 return 0.;
74
75 // Stage 1: u^(1) = u^n + dt * L(u^n)
76 kernel.updateLevelSet(dt);
77
78 if (kernel.velocityUpdateCallback)
79 kernel.velocityUpdateCallback(kernel.levelSets.back());
80
81 // Stage 2: u^(n+1) = 1/2 u^n + 1/2 (u^(1) + dt * L(u^(1)))
82 // Current level set is u^(1). Compute L(u^(1)).
83 kernel.computeRates(dt);
84 // Update to u* = u^(1) + dt * L(u^(1))
85 kernel.updateLevelSet(dt);
86 // Combine: u^(n+1) = 0.5 * u^n + 0.5 * u*
87 kernel.combineLevelSets(0.5, 0.5);
88
89 // If we are in single step mode, the level set will be rebuilt immediately
90 // after this, invalidating the velocity field. Thus, we skip the update.
91 if (kernel.velocityUpdateCallback && !kernel.performOnlySingleStep)
92 kernel.velocityUpdateCallback(kernel.levelSets.back());
93
94 // Finalize
95 kernel.rebuildLS();
96
97 kernel.adjustLowerLayers();
98
99 return dt;
100 }
101
102 static double evolveRungeKutta3(AdvectType &kernel, double maxTimeStep) {
103 // 1. Determine the single time step 'dt' for all stages.
104 kernel.computeRates(maxTimeStep);
105 const double dt = kernel.getCurrentTimeStep();
106
107 // 2. Save u^n (Deep copy to preserve topology)
108 if (kernel.originalLevelSet == nullptr) {
109 kernel.originalLevelSet =
110 viennals::Domain<T, D>::New(kernel.levelSets.back()->getGrid());
111 }
112 kernel.originalLevelSet->deepCopy(kernel.levelSets.back());
113
114 // If dt is 0 or negative, no advection is possible or needed.
115 if (dt <= 0)
116 return 0.;
117
118 // Stage 1: u^(1) = u^n + dt * L(u^n)
119 kernel.updateLevelSet(dt);
120
121 if (kernel.velocityUpdateCallback)
122 kernel.velocityUpdateCallback(kernel.levelSets.back());
123
124 // Stage 2: u^(2) = 3/4 u^n + 1/4 (u^(1) + dt * L(u^(1)))
125 kernel.computeRates(dt);
126 kernel.updateLevelSet(dt);
127 // Combine to get u^(2) = 0.75 * u^n + 0.25 * u*.
128 kernel.combineLevelSets(0.75, 0.25);
129
130 if (kernel.velocityUpdateCallback)
131 kernel.velocityUpdateCallback(kernel.levelSets.back());
132
133 // Stage 3: u^(n+1) = 1/3 u^n + 2/3 (u^(2) + dt * L(u^(2)))
134 kernel.computeRates(dt);
135 kernel.updateLevelSet(dt);
136 // Combine to get u^(n+1) = 1/3 * u^n + 2/3 * u**.
137 kernel.combineLevelSets(1.0 / 3.0, 2.0 / 3.0);
138
139 // If we are in single step mode, the level set will be rebuilt immediately
140 // after this, invalidating the velocity field. Thus, we skip the update.
141 if (kernel.velocityUpdateCallback && !kernel.performOnlySingleStep)
142 kernel.velocityUpdateCallback(kernel.levelSets.back());
143
144 // Finalize: Re-segment and renormalize the final result.
145 kernel.rebuildLS();
146
147 kernel.adjustLowerLayers();
148
149 return dt;
150 }
151};
152
153} // namespace lsInternal
This class is used to advance level sets over time. Level sets are passed to the constructor in a std...
Definition lsAdvect.hpp:54
double getCurrentTimeStep() const
Return the last applied time step.
Definition lsAdvect.hpp:921
static auto New(Args &&...args)
Definition lsDomain.hpp:112
Definition lsAdvectIntegrationSchemes.hpp:41
Definition lsAdvect.hpp:41
SpatialSchemeEnum
Enumeration for the different spatial discretization schemes used by the advection kernel.
Definition lsAdvectIntegrationSchemes.hpp:10
@ LOCAL_LOCAL_LAX_FRIEDRICHS_2ND_ORDER
Definition lsAdvectIntegrationSchemes.hpp:17
@ STENCIL_LOCAL_LAX_FRIEDRICHS_1ST_ORDER
Definition lsAdvectIntegrationSchemes.hpp:20
@ LOCAL_LOCAL_LAX_FRIEDRICHS_1ST_ORDER
Definition lsAdvectIntegrationSchemes.hpp:16
@ LAX_FRIEDRICHS_2ND_ORDER
Definition lsAdvectIntegrationSchemes.hpp:14
@ LOCAL_LAX_FRIEDRICHS_1ST_ORDER
Definition lsAdvectIntegrationSchemes.hpp:18
@ ENGQUIST_OSHER_2ND_ORDER
Definition lsAdvectIntegrationSchemes.hpp:12
@ LAX_FRIEDRICHS_1ST_ORDER
Definition lsAdvectIntegrationSchemes.hpp:13
@ LOCAL_LAX_FRIEDRICHS_2ND_ORDER
Definition lsAdvectIntegrationSchemes.hpp:19
@ WENO_3RD_ORDER
Definition lsAdvectIntegrationSchemes.hpp:21
@ ENGQUIST_OSHER_1ST_ORDER
Definition lsAdvectIntegrationSchemes.hpp:11
@ LOCAL_LAX_FRIEDRICHS_ANALYTICAL_1ST_ORDER
Definition lsAdvectIntegrationSchemes.hpp:15
@ WENO_5TH_ORDER
Definition lsAdvectIntegrationSchemes.hpp:22
TemporalSchemeEnum
Enumeration for the different time integration schemes used to select the advection kernel.
Definition lsAdvectIntegrationSchemes.hpp:31
@ RUNGE_KUTTA_2ND_ORDER
Definition lsAdvectIntegrationSchemes.hpp:33
@ RUNGE_KUTTA_3RD_ORDER
Definition lsAdvectIntegrationSchemes.hpp:34
@ FORWARD_EULER
Definition lsAdvectIntegrationSchemes.hpp:32
Definition lsAdvectIntegrationSchemes.hpp:43
viennals::Advect< T, D > AdvectType
Definition lsAdvectIntegrationSchemes.hpp:44
static double evolveRungeKutta3(AdvectType &kernel, double maxTimeStep)
Definition lsAdvectIntegrationSchemes.hpp:102
static double evolveForwardEuler(AdvectType &kernel, double maxTimeStep)
Definition lsAdvectIntegrationSchemes.hpp:46
static double evolveRungeKutta2(AdvectType &kernel, double maxTimeStep)
Definition lsAdvectIntegrationSchemes.hpp:59