有人说,自己做的都是标量解函数的偏微分方程变分,当遇到解函数是向量值函数时,就不知道有限元空间怎么取,变分也不知道怎么做了。其实是一样的,我这里做个注记。
矩阵内积(Frobenius 含义下的)定义为:
A
:
B
=
∑
i
,
j
a
i
j
b
i
j
A: B=\sum_{i, j} a_{i j} b_{i j}
A:B=i,j∑aijbij
它表示的是矩阵的对应位置相乘最后再求和。
对于矩阵内积,我们有如下性质,
它从如下表达很容易看出:
A
:
B
=
tr
(
A
T
B
)
=
tr
(
A
B
T
)
A: B=\operatorname{tr}\left(A^{T} B\right)=\operatorname{tr}\left(A B^{T}\right)
A:B=tr(ATB)=tr(ABT)
为了方便和统一,我们以后记标量的梯度是个列向量,而矢量的梯度是个矩阵,每一行都表示矢量的某个分量的梯度,即,形如:
∇
f
=
(
f
x
1
f
y
1
f
z
1
f
x
2
f
y
2
f
z
2
)
\nabla \mathbf{f}=\left(f1xf1yf1zf2xf2yf2z
有些地方,关于矢量梯度的定义差一个转置。那么,拉普拉斯算子为:
Δ
f
=
(
Δ
f
1
Δ
f
2
)
\Delta \mathbf{f}=\left(Δf1Δf2
有些人的这两个的定义跟我这里的定义差一个转置。做问题搞程序的时候,要搞清楚有没有转置。
类似于标量函数的有限元空间,考虑向量值函数有限元空间,以二维向量值为例,可以定义为:
V
=
span
{
[
φ
1
0
]
,
…
,
[
φ
m
0
]
,
[
0
φ
1
]
,
…
,
[
0
φ
m
]
}
:
=
span
{
(
ϕ
i
)
}
\mathbf{V}=\operatorname{span}\left\{\left[φ10
所有用到常矩阵 D \mathbf{D} D 的地方,是可以随意进出梯度和散度算子的,即 ∇ D u = D ∇ u \nabla_{} \mathbf{D} \mathbf{u}=\mathbf{D} \nabla_{} \mathbf{u} ∇Du=D∇u ,且 div D u = D div \operatorname{div} \mathbf{D u}=\mathbf{D} \operatorname{div} divDu=Ddiv 。再 一个对于矩阵的散度和梯度算子,是支持分块矩阵的操作的。
有了以上的准备,我们举个简单的例子来看向量值解的方程的变分,
我们考虑这样一个例子:
{
u
t
−
d
u
u
Δ
u
−
d
u
v
Δ
v
=
a
u
(
1
−
u
)
−
b
u
v
u
+
α
v
t
−
d
v
u
Δ
u
−
d
v
v
Δ
v
=
c
u
v
u
+
α
−
d
v
\left\{ut−duuΔu−duvΔv=au(1−u)−buvu+αvt−dvuΔu−dvvΔv=cuvu+α−dv
令
u
=
[
u
,
v
]
T
\mathbf{u}=[u, v]^{T}
u=[u,v]T ,那么上面的方程组可以写为:
u
t
−
D
Δ
u
=
f
(
u
)
\mathbf{u}_{t}-D \Delta{} \mathbf{u}=\mathbf{f}(\mathbf{u})
ut−DΔu=f(u)
做变分就得到:
∫
u
t
⋅
v
+
∫
∇
u
:
∇
(
D
T
v
)
=
∫
f
(
u
)
⋅
v
\int \mathbf{u}_{t} \cdot \mathbf{v}+\int \nabla_{} \mathbf{u}: \nabla_{}\left(D^{T} \mathbf{v}\right)=\int \mathbf{f}(\mathbf{u}) \cdot \mathbf{v}
∫ut⋅v+∫∇u:∇(DTv)=∫f(u)⋅v
或者,
∫
u
t
⋅
v
+
∫
D
∇
u
:
∇
v
=
∫
f
(
u
)
⋅
v
\int \mathbf{u}_{t} \cdot \mathbf{v}+\int D\nabla_{} \mathbf{u}: \nabla_{}\mathbf{v}=\int \mathbf{f}(\mathbf{u}) \cdot \mathbf{v}
∫ut⋅v+∫D∇u:∇v=∫f(u)⋅v
PS:
很多人不太理解,为什么
D
D
D 写在了这个地方,第一个还多了一个转置。这个和我们对向量函数的定义有关。一般来说,我们喜欢把梯度定义为列向量,一列一列地来,但是上述的关于向量值函数的梯度,却是对每个分量求梯度,然后按行排的,这是反直觉的,所以导致了这个地方的
D
D
D 并不是在
u
\mathbf{u}
u 前面。
为了和标量函数的梯度是列向量这个事情统一,假设我修改向量值函数梯度和拉普拉斯的定义如下:
∇
f
=
(
f
x
1
f
y
1
f
z
1
f
x
2
f
y
2
f
z
2
)
T
\nabla \mathbf{f}=\left(f1xf1yf1zf2xf2yf2z
Δ
f
=
(
Δ
f
1
Δ
f
2
)
T
\Delta \mathbf{f}=\left(Δf1Δf2
那么上述问题就应该写为:
u
t
−
(
Δ
u
D
T
)
T
=
f
(
u
)
\mathbf{u}_{t}- (\Delta{} \mathbf{u}D^T)^T=\mathbf{f}(\mathbf{u})
ut−(ΔuDT)T=f(u)
此时我们再做变分,可以得到的是,
∫
u
t
⋅
v
+
∫
∇
u
D
T
:
∇
v
=
∫
f
(
u
)
⋅
v
\int \mathbf{u}_{t} \cdot \mathbf{v}+\int \nabla_{} \mathbf{u}D^T: \nabla_{}\mathbf{v}=\int \mathbf{f}(\mathbf{u}) \cdot \mathbf{v}
∫ut⋅v+∫∇uDT:∇v=∫f(u)⋅v
再在
∇
u
\nabla_{} \mathbf{u}
∇u 和
∇
v
\nabla_{} \mathbf{v}
∇v 头上加转置变回原来的定义方式,就得到了最开始的上述的表达。
这几行 PS 描述,似乎有点扯淡,这是因为这种情况下,只要保持 ∇ u \nabla_{} \mathbf{u} ∇u 和 ∇ v \nabla_{} \mathbf{v} ∇v 定义的方向一致即可,所以不看也罢。
接着考虑向量变分形式的有限元离散,向量有限元空间,定义为:
V
=
span
{
[
φ
1
0
]
,
…
,
[
φ
m
0
]
,
[
0
φ
1
]
,
…
,
[
0
φ
m
]
}
:
=
span
{
(
ϕ
i
)
}
\mathbf{V}=\operatorname{span}\left\{\left[φ10
和标量有限元离散同样的套路,令
u
=
∑
i
=
1
n
u
i
ϕ
i
\mathbf{u}=\sum_{i=1}^{n} u_{i} \phi_{i}
u=i=1∑nuiϕi
依次取
v
=
ϕ
i
\mathbf{v}=\phi_{i}
v=ϕi ,做向量形式的有限元离散,最后可得:
M
u
⃗
t
+
A
u
⃗
=
[
f
u
(
ϕ
i
)
]
n
×
1
M \vec{u}_{t}+A \vec{u}=\left[f_{u}\left(\phi_{i}\right)\right]_{n \times 1}
Mut+Au=[fu(ϕi)]n×1
其中,
M
=
[
∫
ϕ
i
⋅
ϕ
j
]
n
×
n
M=\left[\int \phi_{i} \cdot \phi_{j}\right]_{n \times n}
M=[∫ϕi⋅ϕj]n×n
A
=
[
∫
∇
ϕ
i
:
D
∇
ϕ
j
]
n
×
n
A=\left[\int \nabla_{} \phi_{i}: D\nabla_{} \phi_{j}\right]_{n \times n}
A=[∫∇ϕi:D∇ϕj]n×n
f
u
(
ϕ
i
)
=
∫
f
(
u
)
⋅
ϕ
i
f_{u}\left(\phi_{i}\right)=\int \mathbf{f}(\mathbf{u}) \cdot \phi_{i}
fu(ϕi)=∫f(u)⋅ϕi
事实上,这个离散系统本质上和对原方程组两个式子分别做变分(用同一个测试空间),最后再拼接组合成一个代数方程组是一样的,即:
(
M
s
0
0
M
s
)
u
⃗
t
+
(
d
u
u
A
s
d
u
v
A
s
d
v
u
A
s
d
v
v
A
s
)
u
⃗
=
[
{
f
1
(
u
,
φ
i
)
}
,
{
f
2
(
u
,
φ
i
)
}
]
T
\left(Ms00Ms
这里的
M
s
M_{s}
Ms 和
A
s
A_{s}
As 的下标
s
s
s 表示的是
u
,
v
u, v
u,v 所同属的空间
V
V
V 中的质量矩阵和刚度矩阵。