色散误差
前面的计算中分析了一阶格式的格式粘性,并且提到了一阶格式的格式粘性是泰勒展开的最低阶误差项,因为格式是一阶所以最低阶误差就是二阶项,表现为粘性,因此称为格式粘性。但是前面也有提到泰勒展开的误差项中偶数阶误差项表现为耗散,奇数阶表现为色散。因此其实一阶格式的最高阶误差应当分为奇数阶和偶数阶分别分析。当保留三阶误差项时即可得到一个色散项。这个色散项会使得各频率分量以不同与微分方程描述的传播速度运动,最终经过长时间的推进积累,个频率分量就会分离,产生类似三棱镜对太阳光的作用,因此称为色散。由于一阶迎风格式的耗散很大,在出现明显色散之前就能力就耗散完了,因此这里使用中心差分加人工粘性的做法来简单展示一下色散误差的作用。
具体推进如下
u
i
n
+
1
=
u
i
n
−
Δ
t
2
Δ
x
(
u
i
+
1
n
−
u
i
−
1
n
)
+
ν
Δ
t
Δ
x
2
(
u
i
+
1
n
−
2
u
i
n
+
u
i
−
1
n
)
u_i^{n+1}=u_i^n-\frac{\Delta t}{2\Delta x}(u_{i+1}^n-u_{i-1}^n)+\nu \frac{\Delta t}{\Delta x^2}(u_{i+1}^n-2u_i^n+u_{i-1}^n)
uin+1=uin−2ΔxΔt(ui+1n−ui−1n)+νΔx2Δt(ui+1n−2uin+ui−1n)
#include <iostream>
#include <cmath>
#include <vector>
using namespace std;
const int NE=20,//空间点数
NS=10000,//时间步数
SKIP_STEP=100;
const double rb=-5,l=10,//计算域左边界,计算域长度
dt=0.2,//时间步长
dx=l/NE;
void init_guass(vector<double> &u0)//设置高斯函数初场
{
for(int i=0;i<u0.size();i++)
{
u0[i]=exp(-pow((l*double(i)/(NE-1)+rb),2));
}
}
void advance(vector<double>& u)
{
vector<double> t(u);
double nu=0.02;
for(int i=0;i<u.size()-1;i++)
{
u[i]=t[i]-0.5*(t[i+1]-t[i-1])*dt/dx+nu*(t[i+1]-2*t[i]+t[i-1])/(dx*dx);
}
int i=u.size()-1;
u[i]=t[i]-0.5*(t[0]-t[i-1])*dt/dx+nu*(t[0]-2*t[i]+t[i-1])/(dx*dx);
i=0;
u[i]=t[i]-0.5*(t[i+1]-t[u.size()-1])*dt/dx+nu*(t[i+1]-2*t[i]+t[u.size()-1])/(dx*dx);
}
ostream& operator<<(ostream& out,const vector<double>& A)
{
for(int j=0;j<A.size()-1;j++)
{
out<<A[j]<<'\t';
}
out<<A[A.size()-1];
return out;
}
int main()
{
vector<double> u(NE+1);
init_guass(u);
cout<<NE+1<<'\t'<<NS/SKIP_STEP<<'\t'<<rb<<'\t'<<l<<'\n';
cout<<u<<'\n';
for(int i=0;i<NS;i++)
{
advance(u);
if(NS%SKIP_STEP==0)cout<<u<<'\n';
}
return 0;
}
可以看到随着计算的进行不同频率的波形发生了分离,也就是色散。频率越高的信号色散现象越明显,要消除这种色散就要使得空间步长足够小确保可以分辨相应的信号。
在计算声学中,当声源包含很高频信号时,在传播过程中如果色散过于明显则会使得最终得到的声学信号不准确,因此在计算声学中常常对频散关系做一定的调整,使得相同的网格密度(
Δ
x
\Delta x
Δx)下可以分辨更高波数的信号。
在计算声学中有一个叫PPW(Points Per Wavelength,每波长网格点数量)的格式参数,用于表示当前格式分辨特定波长时需要的网格点数(例如要分辨无量纲波长为0.1的信号,则需要
Δ
x
≤
0.1
P
P
W
\Delta x\le \frac{0.1}{PPW}
Δx≤PPW0.1)。对于一个特定的差分格式,它的PPW越小,就表明其保证高波数(低波长)不发生明显色散所需要的网格数量更少。
基本原理
经典的DRP格式是七点格式,这里为了简单,推导五点格式。因为DRP格式的目的是消除色散误差,因此以没有耗散误差的中心差分格式为基础来进行频散关系优化。
正常五点中心差分格式的阶数是四阶,要满足优化频散关系就需要降阶,为了满足中心差分的对称性,因此五点中心差分格式实际上只有两个参数。这里降阶就是放开一个参数,用于优化频散关系,这样格式会降阶为二阶格式。记五点中心差分的参数分别为
k
1
,
k
2
k_1,k_2
k1,k2则有
∂
u
∂
x
=
k
2
u
i
+
2
+
k
1
u
i
+
1
−
k
1
u
i
−
1
−
k
2
u
i
−
2
\frac{\partial u}{\partial x}=k_2u_{i+2}+k_1u_{i+1}-k_1u_{i-1}-k_2u_{i-2}
∂x∂u=k2ui+2+k1ui+1−k1ui−1−k2ui−2
做泰勒展开后偶数阶展开项都会自动消去。一阶展开项系数需满足为
2
k
2
+
k
1
+
k
1
+
2
k
2
=
1
2k_2+k_1+k_1+2k_2=1
2k2+k1+k1+2k2=1
化简得
k
1
=
1
−
4
k
2
2
k_1=\frac{1-4k_2}{2}
k1=21−4k2
对原差分近似做傅里叶变换得到。
∑
j
α
a
i
e
j
α
x
=
∑
a
i
e
j
α
x
(
k
2
e
2
j
α
Δ
x
+
k
1
e
j
α
Δ
x
−
k
1
e
−
j
α
Δ
x
−
k
2
e
−
2
j
α
Δ
x
)
Δ
x
\sum j\alpha a_ie^{j\alpha x}=\frac{\sum a_ie^{j\alpha x}(k_2e^{2j\alpha \Delta x}+k_1e^{j\alpha \Delta x}-k_1e^{-j\alpha \Delta x}-k_2e^{-2j\alpha \Delta x})}{\Delta x}
∑jαaiejαx=Δx∑aiejαx(k2e2jαΔx+k1ejαΔx−k1e−jαΔx−k2e−2jαΔx)
两边约去相同的量并将
e
j
α
Δ
x
e^{j\alpha \Delta x}
ejαΔx展开化简后得任意波数
α
\alpha
α应满足
α
Δ
x
=
2
(
k
2
s
i
n
(
2
α
Δ
x
)
+
k
1
s
i
n
(
α
Δ
x
)
)
\alpha\Delta x=2(k_2sin(2\alpha\Delta x)+k_1sin(\alpha\Delta x))
αΔx=2(k2sin(2αΔx)+k1sin(αΔx))代入
k
1
,
k
2
k_1,k_2
k1,k2的关系式得到
α
Δ
x
=
(
1
−
4
k
2
)
s
i
n
(
α
Δ
x
)
+
2
k
2
s
i
n
(
2
α
Δ
x
)
\alpha\Delta x=(1-4k_2)sin(\alpha\Delta x)+2k_2sin(2\alpha\Delta x)
αΔx=(1−4k2)sin(αΔx)+2k2sin(2αΔx)令误差
E
=
∫
a
b
(
α
Δ
x
−
2
k
2
s
i
n
(
2
α
Δ
x
)
+
(
4
k
2
−
1
)
s
i
n
(
α
Δ
x
)
)
2
d
(
α
Δ
x
)
E=\int_a^b(\alpha\Delta x-2k_2sin(2\alpha\Delta x)+(4k_2-1)sin(\alpha\Delta x))^2d(\alpha\Delta x)
E=∫ab(αΔx−2k2sin(2αΔx)+(4k2−1)sin(αΔx))2d(αΔx)
所以求解DRP格式的系数就变为了求适当的
k
2
k_2
k2使得
E
E
E取得最小值。
在误差
E
E
E中有两个可调参数
a
,
b
a,b
a,b和一个待求参数
k
2
k_2
k2,
a
,
b
a,b
a,b表示格式需要在哪个范围内保持相应的频散关系。误差
E
E
E积分中的函数是偶函数,因此我们直接取
a
=
0
a=0
a=0,而
b
b
b的值越大我们就能让差分近似在更大的区间
[
a
,
b
]
[a,b]
[a,b]上尽可能的接近原本的微分结果,但是通常
b
b
b越大
E
E
E的最小值也会随之增大。例如当
b
=
π
/
4
b=\pi/4
b=π/4时得到的
E
m
i
n
=
E
1
E_{min}=E_1
Emin=E1,
b
=
π
b=\pi
b=π时得到的
E
m
i
n
=
E
2
E_{min}=E_2
Emin=E2通常
E
2
>
E
1
E_2>E_1
E2>E1。所以我们应当尽可能保持
b
b
b足够大而
E
m
i
n
E_{min}
Emin又足够小。
这里取
b
=
1.2
b=1.2
b=1.2令
∂
E
∂
k
2
=
0
\frac{\partial E}{\partial k_2}=0
∂k2∂E=0解出
k
1
=
0.7090664489143
k
2
=
−
0.1045332244572
\\k_1=\ \ \ 0.7090664489143\\k_2=-0.1045332244572
k1= 0.7090664489143k2=−0.1045332244572
将不同格式的相位变化与
α
Δ
x
\alpha\Delta x
αΔx的关系绘制成曲线如下
可以看到相比于标准的中心差分格式,DRP格式在
α
Δ
x
\alpha\Delta x
αΔx靠近0的位置更加接近精确解。也就是说DRP格式的频散关系更加接近精确解,因此这种方法构造来的格式称为Dispersion Relation Preserving(频散关系保持)格式。
根据绘制的曲线可以看到经过优化大约在
[
0
,
1.1
]
[0,1.1]
[0,1.1]的区间内保证正确的频散关系。由
α
=
2
π
λ
\alpha=\frac{2\pi}{\lambda}
α=λ2π得到
2
π
Δ
x
λ
≤
1.1
\frac{2\pi\Delta x}{\lambda}\le1.1
λ2πΔx≤1.1时频散关系准确。变形后得到
P
P
W
=
λ
Δ
x
≥
2
π
1.1
≈
6
PPW=\frac{\lambda}{\Delta x}\ge\frac{2\pi}{1.1}\approx6
PPW=Δxλ≥1.12π≈6所以改格式的PPW为6,要分辨的最短波长信号
λ
m
i
n
\lambda_{min}
λmin,则空间步长最大为
Δ
x
=
λ
m
i
n
6
\Delta x=\frac{\lambda_{min}}{6}
Δx=6λmin。
同样的方法也可以通过降阶来获得优化的时间推进格式,以及优化的人工粘性(滤波)格式,这里就不再一一介绍了,方程也不再解了。
对流方程
这里就展示一下之前的作业。
题目如下
计算无量纲时间为400时的波形
Δ
x
=
Δ
t
=
0.2
\Delta x=\Delta t=0.2
Δx=Δt=0.2
使用十一点九阶DRP格式,以及优化过的人工粘性和优化的四步三阶R-K方法推进。实线是计算结果,三角是解析结果。可以看到几乎没有任何耗散和色散。
而相同的时间空间步长,使空间用中心差分时间欧拉前差的方法计算结果如下
可以看到计算结果和解析解已经发生了明显的偏移,并且出现了不同波数分量的分离。
非线性方程
题目如下
t=18,36,72时的波形如下
可以看到当存在间断时DRP格式依然可以处理。