Page MenuHomec4science

HelmholtzPadeLagrangeApproximant.py
No OneTemporary

File Metadata

Created
Thu, Oct 31, 12:01

HelmholtzPadeLagrangeApproximant.py

#!/usr/bin/env python3
# -*- coding: utf-8 -*-
from __future__ import print_function
import fenics as fen
import numpy as np
import sympy as sp
from context import FenicsHelmholtzEngine as HFEngine
from context import FenicsHelmholtzScatteringEngine as HFSEngine
from context import FenicsHelmholtzScatteringAugmentedEngine as HFSAEngine
from context import FenicsHSEngine as HSEngine
from context import FenicsHSAugmentedEngine as HSAEngine
from context import ROMApproximantLagrangePade as Pade
PI = np.pi
testNo = 4
if testNo == 1:
params = {'N':4, 'M':3, 'S':5, 'polyBasis':'CHEBYSHEV', 'POD':True}
nu = 12**.5
theta = PI / 3
ztar = 11
x, y = sp.symbols('x[0] x[1]', real=True)
wex = 16/PI**4 * x * y * (x - PI) * (y - PI)
phiex = nu * (x * np.cos(theta) + y * np.sin(theta))
uex = wex * sp.exp(-1.j * phiex)
fex = - uex.diff(x, 2) - uex.diff(y, 2) - nu**2 * uex
nx = ny = 40
mesh = fen.RectangleMesh(fen.Point(0,0), fen.Point(PI,PI), nx, ny)
forcingTerm = [sp.printing.ccode(sp.simplify(sp.re(fex))), sp.printing.ccode(sp.simplify(sp.im(fex)))]
solver = HFEngine(mesh = mesh, wavenumber = nu, forcingTerm = forcingTerm, FEDegree = 3,
DirichletBoundary = 'all', DirichletDatum = 0)
plotter = HSEngine(solver.V)
approx = Pade(solver, plotter, ks = [10 + .5j, 14 + .5j],
w = np.real(nu), approxParameters = params)
approx.plotApp(ztar, name = 'u_Pade''')
approx.plotHF(ztar, name = 'u_HF')
approx.plotErr(ztar, name = 'err')
appErr, solNorm = approx.approxError(ztar), approx.HFNorm(ztar)
print(appErr, solNorm, appErr/solNorm)
print(approx.getPoles(True))
############
elif testNo == 2:
params = {'N':9, 'M':8, 'S':10, 'polyBasis':'CHEBYSHEV', 'POD':True}
ztar = 3.9 ** 2.
n1 = 2**.5
n2 = 3**.5
kappa = 4
theta = PI * 75 / 180
d1, d2 = np.cos(theta), np.sin(theta)
K1 = kappa * n1 * d1
if kappa * n2 >= K1:
K2 = ((kappa*n2)**2 - K1**2)**.5
else:
K2 = 1.j * (K1**2 - (kappa*n2)**2)**.5
R = (kappa * n1 * d2 - K2) / (kappa * n1 * d2 + K2)
T = R + 1
x, y = sp.symbols('x[0] x[1]', real=True)
uex1 = T*sp.exp(1.j*(K1*x+K2*y))
uex2 = sp.exp(1.j*kappa*n1*(d1*x+d2*y)) + R*sp.exp(1.j*kappa*n1*(d1*x-d2*y))
# Exact solution
uexRe = fen.Expression('x[1]>=0 ? {0} : {1}'.format(\
sp.printing.ccode(sp.re(uex1)), sp.printing.ccode(sp.re(uex2))), degree=4)
uexIm = fen.Expression('x[1]>=0 ? {0} : {1}'.format(\
sp.printing.ccode(sp.im(uex1)), sp.printing.ccode(sp.im(uex2))), degree=4)
# wavenumber term
nRe = fen.Expression('x[1]<0 ? n1r : n2r', n1r = n1.real, n2r = n2.real, degree=4)
nIm = fen.Expression('x[1]<0 ? n1i : n2i', n1i = n1.imag, n2i = n2.imag, degree=4)
# Create mesh and define function space
nx = ny = 50
mesh = fen.RectangleMesh(fen.Point(-PI/2,-PI/2), fen.Point(PI/2,PI/2), nx, ny)
solver = HFEngine(mesh = mesh, wavenumber = kappa, refractionIndex = (nRe, nIm),
forcingTerm = 0, FEDegree = 3, DirichletBoundary = 'all',
DirichletDatum = (uexRe, uexIm))
plotter = HSEngine(solver.V)
approx = Pade(solver, plotter, ks = np.power([3.85 + .15j, 4.15 + .15j], 2.),
w = kappa, approxParameters = params, plotSnapshots = True)
approx.plotApp(ztar, name = 'u_Pade''')
approx.plotHF(ztar, name = 'u_HF')
approx.plotErr(ztar, name = 'err')
appErr, solNorm = approx.approxError(ztar), approx.HFNorm(ztar)
print(appErr, solNorm, appErr/solNorm)
print(approx.getPoles(True))
############
elif testNo == 3:
def Dboundary(x, on_boundary):
return on_boundary and (fen.near(x[0], 0) or fen.near(x[0], PI))
A = 10
kappa = 4
theta = PI * 90 / 180
x, y = sp.symbols('x[0] x[1]', real=True)
phiex = kappa * (x * np.cos(theta) + y * np.sin(theta))
u0ex = - A * sp.exp(1.j * phiex)
nx = ny = 40
mesh = fen.RectangleMesh(fen.Point(0,0), fen.Point(PI,PI), nx, ny)
DirichletTerm = [sp.printing.ccode(sp.simplify(sp.re(u0ex))), sp.printing.ccode(sp.simplify(sp.im(u0ex)))]
params = {'N':40, 'M':39, 'S':45, 'polyBasis':'CHEBYSHEV', 'POD':True}
solver = HFSEngine(mesh = mesh, wavenumber = kappa, forcingTerm = 0,
FEDegree = 3, DirichletBoundary = Dboundary,
RobinBoundary = 'rest', DirichletDatum = DirichletTerm)
plotter = HSEngine(solver.V)
approx = Pade(solver, plotter, ks = [0, 8],
approxParameters = params,
plotSnapshots = False)
print(approx.getPoles(True))
ktar = 4.5
approx.plotApp(ktar, name = 'u_Pade''')
approx.plotHF(ktar, name = 'u_HF')
approx.plotErr(ktar, name = 'err')
appErr, solNorm = approx.approxError(ktar), approx.HFNorm(ktar)
print(appErr, solNorm, appErr/solNorm)
############
elif testNo == 4:
def Dboundary(x, on_boundary):
return on_boundary and (fen.near(x[0], 0) or fen.near(x[0], PI))
A = 10
kappa = 4
theta = PI * 90 / 180
x, y = sp.symbols('x[0] x[1]', real=True)
phiex = kappa * (x * np.cos(theta) + y * np.sin(theta))
u0ex = - A * sp.exp(1.j * phiex)
nx = ny = 40
mesh = fen.RectangleMesh(fen.Point(0,0), fen.Point(PI,PI), nx, ny)
DirichletTerm = [sp.printing.ccode(sp.simplify(sp.re(u0ex))), sp.printing.ccode(sp.simplify(sp.im(u0ex)))]
params = {'N':40, 'M':39, 'S':45, 'polyBasis':'CHEBYSHEV', 'POD':True}
solver = HFSAEngine(mesh = mesh, wavenumber = kappa, forcingTerm = 0,
FEDegree = 3, DirichletBoundary = Dboundary,
RobinBoundary = 'rest', DirichletDatum = DirichletTerm,
constraintType = 'IDENTITY')
plotter = HSAEngine(solver.V, 2)
approx = Pade(solver, plotter, ks = [0, 8],
approxParameters = params,
plotSnapshots = False)
ktar = 4.5
approx.plotApp(ktar, name = 'u_Pade''')
approx.plotHF(ktar, name = 'u_HF')
approx.plotErr(ktar, name = 'err')
appErr, solNorm = approx.approxError(ktar, kappa), approx.HFNorm(ktar, kappa)
print(appErr, solNorm, np.divide(appErr, solNorm))
print(approx.getPoles(True))

Event Timeline