Skip to content

Commit c0c42ce

Browse files
authored
Merge pull request #323 from FourierFlows/ncc/add-palinstrophy
Add palinstrophy diagnostic in `TwoDNavierStokes`
2 parents dc05d4d + 9ad3212 commit c0c42ce

4 files changed

Lines changed: 70 additions & 22 deletions

File tree

Project.toml

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ name = "GeophysicalFlows"
22
uuid = "44ee3b1c-bc02-53fa-8355-8e347616e15e"
33
license = "MIT"
44
authors = ["Navid C. Constantinou <navidcy@gmail.com>", "Gregory L. Wagner <wagner.greg@gmail.com>", "and co-contributors"]
5-
version = "0.15.1"
5+
version = "0.15.2"
66

77
[deps]
88
CUDA = "052768ef-5323-5732-b1bb-66c8b64840ba"
@@ -18,15 +18,15 @@ StaticArrays = "90137ffa-7385-5640-81b9-e52037218182"
1818
Statistics = "10745b16-79ce-11e8-11f9-7d13ad32a3b2"
1919

2020
[compat]
21-
CUDA = "^1, ^2.4.2, 3.0.0 - 3.6.4, ^3.7.1, 4"
22-
DocStringExtensions = "^0.8, 0.9"
23-
FFTW = "^1"
24-
FourierFlows = "^0.10.0"
25-
JLD2 = "^0.1, ^0.2, ^0.3, ^0.4"
26-
Reexport = "^0.2, ^1"
27-
SpecialFunctions = "^0.10, ^1, 2"
28-
StaticArrays = "^0.12, ^1"
29-
julia = "^1.6"
21+
CUDA = "1, 2.4.2, 3.0.0 - 3.6.4, 3.7.1, 4"
22+
DocStringExtensions = "0.8, 0.9"
23+
FFTW = "1"
24+
FourierFlows = "0.10.3"
25+
JLD2 = "0.1, 0.2, 0.3, 0.4"
26+
Reexport = "0.2, 1"
27+
SpecialFunctions = "0.10, 1, 2"
28+
StaticArrays = "0.12, 1"
29+
julia = "1.6"
3030

3131
[extras]
3232
BenchmarkTools = "6e4b80f9-dd63-53aa-95a3-0cdb28fa8baf"

src/twodnavierstokes.jl

Lines changed: 20 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -382,7 +382,7 @@ end
382382
"""
383383
enstrophy(prob)
384384
385-
Returns the problem's (`prob`) domain-averaged enstrophy,
385+
Return the problem's (`prob`) domain-averaged enstrophy,
386386
387387
```math
388388
\\int \\frac1{2} ζ² \\frac{𝖽x 𝖽y}{L_x L_y} = \\sum_{𝐤} \\frac1{2} |ζ̂|² ,
@@ -392,6 +392,25 @@ where ``ζ`` is the relative vorticity.
392392
"""
393393
@inline enstrophy(prob) = 1 / (2 * prob.grid.Lx * prob.grid.Ly) * parsevalsum(abs2.(prob.sol), prob.grid)
394394

395+
"""
396+
palinstrophy(prob)
397+
398+
Return the problem's (`prob`) domain-averaged palinstrophy,
399+
400+
```math
401+
\\int \\frac1{2} |{\\bf ∇} ζ|² \\frac{𝖽x 𝖽y}{L_x L_y} = \\sum_{𝐤} \\frac1{2} |𝐤|² |ζ̂|² ,
402+
```
403+
404+
where ``ζ`` is the relative vorticity.
405+
"""
406+
@inline function palinstrophy(prob)
407+
sol, vars, grid = prob.sol, prob.vars, prob.grid
408+
palinstrophyh = vars.uh # use vars.uh as scratch variable
409+
410+
@. palinstrophyh = 1 / 2 * grid.Krsq * abs2(sol)
411+
return 1 / (grid.Lx * grid.Ly) * parsevalsum(palinstrophyh, grid)
412+
end
413+
395414
"""
396415
energy_dissipation(prob, ξ, νξ)
397416

test/runtests.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ for dev in devices
4646
@test test_twodnavierstokes_stochasticforcing_energybudget(dev)
4747
@test test_twodnavierstokes_deterministicforcing_enstrophybudget(dev)
4848
@test test_twodnavierstokes_stochasticforcing_enstrophybudget(dev)
49-
@test test_twodnavierstokes_energyenstrophy(dev)
49+
@test test_twodnavierstokes_energyenstrophypalinstrophy(dev)
5050
@test test_twodnavierstokes_problemtype(dev, Float32)
5151
@test TwoDNavierStokes.nothingfunction() == nothing
5252
end

test/test_twodnavierstokes.jl

Lines changed: 39 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -257,19 +257,46 @@ function test_twodnavierstokes_advection(dt, stepper, dev::Device=CPU(); n=128,
257257
isapprox(prob.vars.ζ, ζf, rtol=rtol_twodnavierstokes)
258258
end
259259

260-
function test_twodnavierstokes_energyenstrophy(dev::Device=CPU())
260+
function test_twodnavierstokes_energyenstrophypalinstrophy(dev::Device=CPU())
261261
nx, Lx = 128, 2π
262262
ny, Ly = 126, 3π
263263

264264
grid = TwoDGrid(dev; nx, Lx, ny, Ly)
265265
x, y = gridpoints(grid)
266266

267267
k₀, l₀ = 2π/grid.Lx, 2π/grid.Ly # fundamental wavenumbers
268-
ψ₀ = @. sin(2k₀*x)*cos(2l₀*y) + 2sin(k₀*x)*cos(3l₀*y)
269-
ζ₀ = @. -((2k₀)^2+(2l₀)^2)*sin(2k₀*x)*cos(2l₀*y) - (k₀^2+(3l₀)^2)*2sin(k₀*x)*cos(3l₀*y)
268+
ψ₀ = @. sin(2k₀ * x) * cos(2l₀ * y) + 2sin(k₀ * x) * cos(3l₀ * y)
269+
ζ₀ = @. -((2k₀)^2 + (2l₀)^2) * sin(2k₀ * x) * cos(2l₀ * y) - (k₀^2 + (3l₀)^2) * 2sin(k₀ * x) * cos(3l₀ * y)
270270

271-
energy_calc = 29/9
272-
enstrophy_calc = 2701/162
271+
#=
272+
273+
We can analytically compute the energy, enstrophy, and palinstrophy
274+
that corresponds to the above initial condition using Mathematica
275+
276+
k0 = 2 Pi/Lx; l0 = 2 Pi/Ly;
277+
278+
psi[x_, y_] = Sin[2 k0 x] Cos[2 l0 y] + 2 Sin[k0 x] Cos[3 l0 y];
279+
u[x, y] = -D[psi[x, y], y];
280+
v[x, y] = D[psi[x, y], x];
281+
zeta[x, y] = D[v[x, y], x] - D[u[x, y], y];
282+
283+
E0 = Integrate[
284+
1/2 (u[x, y]^2 + v[x, y]^2), {x, 0, Lx}, {y, 0, Ly}] / (Lx Ly);
285+
E0 /. {Lx -> 2 Pi, Ly -> 3 Pi}
286+
287+
Z0 = Integrate[1/2 zeta[x, y]^2, {x, 0, Lx}, {y, 0, Ly}] / (Lx Ly);
288+
Z0 /. {Lx -> 2 Pi, Ly -> 3 Pi}
289+
290+
P0 = Integrate[
291+
1/2 (D[zeta[x, y], x]^2 + D[zeta[x, y], y]^2), {x, 0, Lx}, {y, 0,
292+
Ly}] / (Lx Ly);
293+
P0 /. {Lx -> 2 Pi, Ly -> 3 Pi}
294+
295+
=#
296+
297+
energy_analytic = 29/9
298+
enstrophy_analytic = 2701/162
299+
palinstrophy_analytic = 126277/1458
273300

274301
prob = TwoDNavierStokes.Problem(dev; nx, Lx, ny, Ly, stepper="ForwardEuler")
275302

@@ -278,14 +305,16 @@ function test_twodnavierstokes_energyenstrophy(dev::Device=CPU())
278305
TwoDNavierStokes.set_ζ!(prob, ζ₀)
279306
TwoDNavierStokes.updatevars!(prob)
280307

281-
energyζ₀ = TwoDNavierStokes.energy(prob)
282-
enstrophyζ₀ = TwoDNavierStokes.enstrophy(prob)
308+
energy₀ = TwoDNavierStokes.energy(prob)
309+
enstrophy₀ = TwoDNavierStokes.enstrophy(prob)
310+
palinstrophy₀ = TwoDNavierStokes.palinstrophy(prob)
283311

284312
params = TwoDNavierStokes.Params(p.ν, p.nν)
285313

286-
(isapprox(energyζ₀, energy_calc, rtol=rtol_twodnavierstokes) &&
287-
isapprox(enstrophyζ₀, enstrophy_calc, rtol=rtol_twodnavierstokes) &&
288-
TwoDNavierStokes.addforcing!(prob.timestepper.N, sol, cl.t, cl, v, p, g)==nothing && p == params)
314+
return (isapprox(energy₀, energy_analytic, rtol=rtol_twodnavierstokes) &&
315+
isapprox(enstrophy₀, enstrophy_analytic, rtol=rtol_twodnavierstokes) &&
316+
isapprox(palinstrophy₀, palinstrophy_analytic, rtol=rtol_twodnavierstokes) &&
317+
TwoDNavierStokes.addforcing!(prob.timestepper.N, sol, cl.t, cl, v, p, g)==nothing && p == params)
289318
end
290319

291320
function test_twodnavierstokes_problemtype(dev, T)

0 commit comments

Comments
 (0)