Skip to content

Commit 52a0ac1

Browse files
Harsh SinghHarsh Singh
authored andcommitted
Add IMEX Runge-Kutta solvers (ARS, SSP, BHR) with ESDIRK implicit structure and proper cache handling
1 parent 703ed84 commit 52a0ac1

6 files changed

Lines changed: 1452 additions & 1 deletion

File tree

lib/OrdinaryDiffEqSDIRK/src/OrdinaryDiffEqSDIRK.jl

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,8 @@ export ImplicitEuler, ImplicitMidpoint, Trapezoid, TRBDF2, SDIRK2, SDIRK22,
4444
SFSDIRK5, CFNLIRK3, SFSDIRK6, SFSDIRK7, SFSDIRK8, Kvaerno5, KenCarp4, KenCarp5,
4545
SFSDIRK4, SFSDIRK5, CFNLIRK3, SFSDIRK6,
4646
SFSDIRK7, SFSDIRK8, ESDIRK436L2SA2, ESDIRK437L2SA, ESDIRK547L2SA2, ESDIRK659L2SA,
47-
IMEXSSP222, IMEXSSP2322, IMEXSSP3332, IMEXSSP3433
47+
IMEXSSP222, IMEXSSP2322, IMEXSSP3332, IMEXSSP3433,
48+
ARS222, ARS232, ARS443, BHR553
4849

4950
import PrecompileTools
5051
import Preferences

lib/OrdinaryDiffEqSDIRK/src/alg_utils.jl

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,11 @@ ssp_coefficient(alg::SSPSDIRK2) = 4
5151

5252
isesdirk(alg::TRBDF2) = true
5353

54+
isesdirk(alg::ARS222) = true
55+
isesdirk(alg::ARS232) = true
56+
isesdirk(alg::ARS443) = true
57+
isesdirk(alg::BHR553) = true
58+
5459
issplit(alg::KenCarp3) = true
5560
issplit(alg::KenCarp4) = true
5661
issplit(alg::KenCarp47) = true
@@ -62,7 +67,17 @@ issplit(alg::IMEXSSP2322) = true
6267
issplit(alg::IMEXSSP3332) = true
6368
issplit(alg::IMEXSSP3433) = true
6469

70+
issplit(alg::ARS222) = true
71+
issplit(alg::ARS232) = true
72+
issplit(alg::ARS443) = true
73+
issplit(alg::BHR553) = true
74+
6575
alg_order(alg::IMEXSSP222) = 2
6676
alg_order(alg::IMEXSSP2322) = 2
6777
alg_order(alg::IMEXSSP3332) = 2
6878
alg_order(alg::IMEXSSP3433) = 3
79+
80+
alg_order(alg::ARS222) = 2
81+
alg_order(alg::ARS232) = 2
82+
alg_order(alg::ARS443) = 3
83+
alg_order(alg::BHR553) = 3

lib/OrdinaryDiffEqSDIRK/src/algorithms.jl

Lines changed: 166 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1773,3 +1773,169 @@ function IMEXSSP3433(;
17731773
_unwrap_val(concrete_jac), typeof(step_limiter!),
17741774
}(linsolve, nlsolve, precs, extrapolant, step_limiter!, AD_choice)
17751775
end
1776+
1777+
const _ARS_BHR_REFERENCE = "@article{ascher1997implicit,
1778+
title={Implicit-explicit Runge-Kutta methods for time-dependent partial differential equations},
1779+
author={Ascher, Uri M and Ruuth, Steven J and Spiteri, Raymond J},
1780+
journal={Applied Numerical Mathematics},
1781+
volume={25},
1782+
number={2-3},
1783+
pages={151--167},
1784+
year={1997},
1785+
publisher={Elsevier}}"
1786+
1787+
@doc SDIRK_docstring(
1788+
"3-stage 2nd-order IMEX ESDIRK method (ARS(2,2,2)) for split ODEs. From Ascher, Ruuth & Spiteri (1997), Table II.",
1789+
"ARS222";
1790+
references = _ARS_BHR_REFERENCE,
1791+
extra_keyword_description = """
1792+
- `extrapolant`: TBD
1793+
- `step_limiter!`: function of the form `limiter!(u, integrator, p, t)`
1794+
""",
1795+
extra_keyword_default = """
1796+
extrapolant = :linear,
1797+
step_limiter! = trivial_limiter!,
1798+
"""
1799+
)
1800+
struct ARS222{CS, AD, F, F2, P, FDT, ST, CJ, StepLimiter} <:
1801+
OrdinaryDiffEqNewtonAlgorithm{CS, AD, FDT, ST, CJ}
1802+
linsolve::F
1803+
nlsolve::F2
1804+
precs::P
1805+
extrapolant::Symbol
1806+
step_limiter!::StepLimiter
1807+
autodiff::AD
1808+
end
1809+
function ARS222(;
1810+
chunk_size = Val{0}(), autodiff = AutoForwardDiff(),
1811+
standardtag = Val{true}(), concrete_jac = nothing,
1812+
diff_type = Val{:forward}(),
1813+
linsolve = nothing, precs = DEFAULT_PRECS, nlsolve = NLNewton(),
1814+
extrapolant = :linear, step_limiter! = trivial_limiter!
1815+
)
1816+
AD_choice, chunk_size, diff_type = _process_AD_choice(autodiff, chunk_size, diff_type)
1817+
return ARS222{
1818+
_unwrap_val(chunk_size), typeof(AD_choice), typeof(linsolve),
1819+
typeof(nlsolve), typeof(precs), diff_type, _unwrap_val(standardtag),
1820+
_unwrap_val(concrete_jac), typeof(step_limiter!),
1821+
}(linsolve, nlsolve, precs, extrapolant, step_limiter!, AD_choice)
1822+
end
1823+
1824+
@doc SDIRK_docstring(
1825+
"3-stage 2nd-order IMEX ESDIRK method (ARS(2,3,2)) for split ODEs. From Ascher, Ruuth & Spiteri (1997).",
1826+
"ARS232";
1827+
references = _ARS_BHR_REFERENCE,
1828+
extra_keyword_description = """
1829+
- `extrapolant`: TBD
1830+
- `step_limiter!`: function of the form `limiter!(u, integrator, p, t)`
1831+
""",
1832+
extra_keyword_default = """
1833+
extrapolant = :linear,
1834+
step_limiter! = trivial_limiter!,
1835+
"""
1836+
)
1837+
struct ARS232{CS, AD, F, F2, P, FDT, ST, CJ, StepLimiter} <:
1838+
OrdinaryDiffEqNewtonAlgorithm{CS, AD, FDT, ST, CJ}
1839+
linsolve::F
1840+
nlsolve::F2
1841+
precs::P
1842+
extrapolant::Symbol
1843+
step_limiter!::StepLimiter
1844+
autodiff::AD
1845+
end
1846+
function ARS232(;
1847+
chunk_size = Val{0}(), autodiff = AutoForwardDiff(),
1848+
standardtag = Val{true}(), concrete_jac = nothing,
1849+
diff_type = Val{:forward}(),
1850+
linsolve = nothing, precs = DEFAULT_PRECS, nlsolve = NLNewton(),
1851+
extrapolant = :linear, step_limiter! = trivial_limiter!
1852+
)
1853+
AD_choice, chunk_size, diff_type = _process_AD_choice(autodiff, chunk_size, diff_type)
1854+
return ARS232{
1855+
_unwrap_val(chunk_size), typeof(AD_choice), typeof(linsolve),
1856+
typeof(nlsolve), typeof(precs), diff_type, _unwrap_val(standardtag),
1857+
_unwrap_val(concrete_jac), typeof(step_limiter!),
1858+
}(linsolve, nlsolve, precs, extrapolant, step_limiter!, AD_choice)
1859+
end
1860+
1861+
@doc SDIRK_docstring(
1862+
"5-stage 3rd-order IMEX ESDIRK method (ARS(4,4,3)) for split ODEs. From Ascher, Ruuth & Spiteri (1997), Table IV.",
1863+
"ARS443";
1864+
references = _ARS_BHR_REFERENCE,
1865+
extra_keyword_description = """
1866+
- `extrapolant`: TBD
1867+
- `step_limiter!`: function of the form `limiter!(u, integrator, p, t)`
1868+
""",
1869+
extra_keyword_default = """
1870+
extrapolant = :linear,
1871+
step_limiter! = trivial_limiter!,
1872+
"""
1873+
)
1874+
struct ARS443{CS, AD, F, F2, P, FDT, ST, CJ, StepLimiter} <:
1875+
OrdinaryDiffEqNewtonAlgorithm{CS, AD, FDT, ST, CJ}
1876+
linsolve::F
1877+
nlsolve::F2
1878+
precs::P
1879+
extrapolant::Symbol
1880+
step_limiter!::StepLimiter
1881+
autodiff::AD
1882+
end
1883+
function ARS443(;
1884+
chunk_size = Val{0}(), autodiff = AutoForwardDiff(),
1885+
standardtag = Val{true}(), concrete_jac = nothing,
1886+
diff_type = Val{:forward}(),
1887+
linsolve = nothing, precs = DEFAULT_PRECS, nlsolve = NLNewton(),
1888+
extrapolant = :linear, step_limiter! = trivial_limiter!
1889+
)
1890+
AD_choice, chunk_size, diff_type = _process_AD_choice(autodiff, chunk_size, diff_type)
1891+
return ARS443{
1892+
_unwrap_val(chunk_size), typeof(AD_choice), typeof(linsolve),
1893+
typeof(nlsolve), typeof(precs), diff_type, _unwrap_val(standardtag),
1894+
_unwrap_val(concrete_jac), typeof(step_limiter!),
1895+
}(linsolve, nlsolve, precs, extrapolant, step_limiter!, AD_choice)
1896+
end
1897+
1898+
@doc SDIRK_docstring(
1899+
"5-stage 3rd-order IMEX ESDIRK method (BHR(5,5,3)*) for split ODEs. From Boscarino & Russo (2009).",
1900+
"BHR553";
1901+
references = "@article{boscarino2009error,
1902+
title={Error analysis of IMEX Runge-Kutta methods derived from differential-algebraic systems},
1903+
author={Boscarino, Sebastiano and Russo, Giovanni},
1904+
journal={SIAM Journal on Numerical Analysis},
1905+
volume={49},
1906+
number={4},
1907+
pages={1600--1624},
1908+
year={2009},
1909+
publisher={SIAM}}",
1910+
extra_keyword_description = """
1911+
- `extrapolant`: TBD
1912+
- `step_limiter!`: function of the form `limiter!(u, integrator, p, t)`
1913+
""",
1914+
extra_keyword_default = """
1915+
extrapolant = :linear,
1916+
step_limiter! = trivial_limiter!,
1917+
"""
1918+
)
1919+
struct BHR553{CS, AD, F, F2, P, FDT, ST, CJ, StepLimiter} <:
1920+
OrdinaryDiffEqNewtonAlgorithm{CS, AD, FDT, ST, CJ}
1921+
linsolve::F
1922+
nlsolve::F2
1923+
precs::P
1924+
extrapolant::Symbol
1925+
step_limiter!::StepLimiter
1926+
autodiff::AD
1927+
end
1928+
function BHR553(;
1929+
chunk_size = Val{0}(), autodiff = AutoForwardDiff(),
1930+
standardtag = Val{true}(), concrete_jac = nothing,
1931+
diff_type = Val{:forward}(),
1932+
linsolve = nothing, precs = DEFAULT_PRECS, nlsolve = NLNewton(),
1933+
extrapolant = :linear, step_limiter! = trivial_limiter!
1934+
)
1935+
AD_choice, chunk_size, diff_type = _process_AD_choice(autodiff, chunk_size, diff_type)
1936+
return BHR553{
1937+
_unwrap_val(chunk_size), typeof(AD_choice), typeof(linsolve),
1938+
typeof(nlsolve), typeof(precs), diff_type, _unwrap_val(standardtag),
1939+
_unwrap_val(concrete_jac), typeof(step_limiter!),
1940+
}(linsolve, nlsolve, precs, extrapolant, step_limiter!, AD_choice)
1941+
end

0 commit comments

Comments
 (0)