一、问题描述
对于线性方程组
A x = b , A = ( b 1 c 1 a 2 b 2 c 2 ⋱ ⋱ ⋱ ⋱ ⋱ ⋱ a n − 1 b n − 1 c n − 1 a n b n ) , b = ( f 1 f 2 ⋮ f n ) Ax=b,\quad A=\begin{pmatrix}b_1&c_1&&&&\\a_2&b_2&c_2&&&\\&\ddots&\ddots&\ddots&& \\&&\ddots&\ddots&\ddots& \\&&&a_{n-1}&b_{n-1}&c_{n-1}\\&&&&a_n&b_n\end{pmatrix},\quad b=\begin{pmatrix} f_1\\f_2\\ \vdots\\ f_n \end{pmatrix} Ax=b,A= b1a2c1b2⋱c2⋱⋱⋱⋱an−1⋱bn−1ancn−1bn ,b= f1f2⋮fn
其中
{ ∣ b 1 ∣ > ∣ c 1 ∣ > 0 ∣ b n ∣ > ∣ a n ∣ > 0 ∣ b i ∣ ≥ ∣ a i ∣ + ∣ c i ∣ , a i c i ≠ 0 , i = 2 , 3 , ⋯ n − 1 \begin{cases} \begin{aligned}&\quad|b_1|>|c_1|>0\\&\quad|b_n|>|a_n|>0\\&\quad|b_i|\geq|a_i|+|c_i|,\quad a_ic_i\neq0,i=2,3,\cdots n-1\end{aligned} \end{cases} ⎩ ⎨ ⎧∣b1∣>∣c1∣>0∣bn∣>∣an∣>0∣bi∣≥∣ai∣+∣ci∣,aici=0,i=2,3,⋯n−1
二、追赶法解三对角方程组
A = ( b 1 c 1 a 2 b 2 c 2 ⋱ ⋱ ⋱ a n − 1 b n − 1 c n − 1 a n b n ) , L = ( 1 l 2 1 l 3 ⋱ ⋱ 1 l n 1 ) , U = ( u 1 d 1 u 2 d 2 ⋱ ⋱ u n − 1 d n − 1 u n ) \begin{equation*} A=\begin{pmatrix}b_1&c_1\\a_2&b_2&c_2\\&\ddots&\ddots&\ddots\\&&a_{n-1}&b_{n-1}&c_{n-1}\\&&&a_n&b_n\end{pmatrix}, {L}=\begin{pmatrix}1\\l_2&1\\&l_3&\ddots\\&&\ddots&1\\&&&l_n&1\end{pmatrix},{U}=\begin{pmatrix}u_1&d_1\\&u_2&d_2\\&&\ddots&\ddots\\&&&u_{n-1}&d_{n-1}\\&&&&u_n\end{pmatrix} \end{equation*} A= b1a2c1b2⋱c2⋱an−1⋱bn−1ancn−1bn ,L= 1l21l3⋱⋱1ln1 ,U= u1d1u2d2⋱⋱un−1dn−1un
A = L U A = LU A=LU
首先通过前两行与前两列可以知道
b 1 = u 1 , a 2 = l 2 u 1 , c 1 = d 1 b_1=u_1,a_2 = l_2u_1,c_1 = d_1 b1=u1,a2=l2u1,c1=d1得 u 1 , d 1 , l 2 u_1,d_1,l_2 u1,d1,l2
再从下式看两边是如何对应上的
A : i − 1 i i + 1 i a i b i c i A:\begin{array}{c|c|c|c} & i-1 &i&i+1\\ \hline i&a_i&b_i&c_i \end{array} A:ii−1aiibii+1ci
L : i − 1 i i + 1 i l i 1 U : i − 1 i i + 1 i − 2 d i − 2 i − 1 u i − 1 d i − 1 i u i d i i + 1 u i + 1 L:\begin{array}{c|c|c|c} & i-1 &i&i+1\\ \hline i&l_i&1& \end{array} \quad U:\begin{array}{c|c|c|c} & i-1 &i&i+1\\ \hline i-2&d_{i-2}& &\\ \hline i-1&u_{i-1}&d_{i-1}&\\\hline i& & u_i&d_i\\\hline i+1 & & &u_{i+1} \end{array} L:ii−1lii1i+1U:i−2i−1ii+1i−1di−2ui−1idi−1uii+1diui+1
可以看出
a i = l i u i − 1 b i = l i d i − 1 + u i c i = d i \begin{aligned} &a_i = l_i u_{i-1}\\ &b_i = l_i d_{i-1} +u_i\\ &c_i = d_i \end{aligned} ai=liui−1bi=lidi−1+uici=di
d i d_i di已经得出,接下来只需算 l i l_i li 与 u i u_i ui 即可
再有 u 1 = b 1 u_1 = b_1 u1=b1, i = 2 → n i = 2 \to n i=2→n
l i = a i u i − 1 u i = b i − l i ⋅ c i − 1 \begin{gathered} l_i = \dfrac{a_i}{u_{i-1}}\\ u_i = b_i - l_i \cdot c_{i-1} \end{gathered} li=ui−1aiui=bi−li⋅ci−1
这样子, L L L 和 U U U就得到了
接下来,解 L y = b Ly = b Ly=b , U x = y Ux = y Ux=y,这一步可以用之前写好的程序直接解出
由于这里,结果比较简易,直接将结果写了出来:
解 L y = b Ly = b Ly=b: (追)
( 1 l 2 1 l 3 ⋱ ⋱ 1 l n 1 ) ( y 1 y 2 ⋮ y n − 1 y n ) = ( f 1 f 2 ⋮ f n − 1 f n ) \left.\begin{pmatrix}1\\l_2&1\\&l_3&\ddots\\&&\ddots&1\\&&&l_n&1\end{pmatrix}\left(\begin{array}{c}y_1\\y_2\\\vdots\\y_{n-1}\\y_n\end{array}\right.\right)=\left(\begin{array}{c}f_1\\f_2\\\vdots\\f_{n-1}\\f_n\end{array}\right) 1l21l3⋱⋱1ln1 y1y2⋮yn−1yn = f1f2⋮fn−1fn
y 1 = f 1 , y i = f i − l i ⋅ y i − 1 ( i = 2 , 3 ⋯ n ) y_1 = f_1,y_i = f_i - l_i \cdot y_{i-1} (i=2,3\cdots n) y1=f1,yi=fi−li⋅yi−1(i=2,3⋯n)
解 U x = y Ux = y Ux=y:(赶)
( u 1 d 1 u 2 d 2 ⋱ ⋱ u n − 1 d n − 1 u n ) ( x 1 x 2 ⋮ x n − 1 x n ) = ( y 1 y 2 ⋮ y n − 1 y n ) \left.\begin{pmatrix}u_1&d_1&&&\\&u_2&d_2&&\\&&\ddots&\ddots&\\&&&u_{n-1}&d_{n-1}\\&&&&u_n\end{pmatrix}\left(\begin{array}{c}x_1\\x_2\\\vdots\\x_{n-1}\\x_n\end{array}\right.\right)=\left(\begin{array}{c}y_1\\y_2\\\vdots\\y_{n-1}\\y_n\end{array}\right) u1d1u2d2⋱⋱un−1dn−1un x1x2⋮xn−1xn = y1y2⋮yn−1yn
x n = y n u n , x i = ( y i − d i ⋅ x i + 1 ) u i ( i = n − 1 , ⋯ , 2 , 1 ) x_n = \dfrac{y_n}{u_n}, x_i = \dfrac{(y_i-d_i\cdot x_{i+1})}{u_i}(i=n-1 ,\cdots,2, 1) xn=unyn,xi=ui(yi−di⋅xi+1)(i=n−1,⋯,2,1)
这样 x x x 就求出来了
三、算法
四、北太天元源代码
function [x]=tridiag_chase(A,f)% 追赶法解三对角方程组% 输入: 适用的三对角矩阵A, 右端向量f% 输出: 解,列向量的形式 x% 创建时间: 1/26/2024% 版本: 1.0n = length(A);% 将三对角提取出来b = diag(A,0); a = diag(A,-1); c = diag(A,1);% 处理一下角标 a是从a_2开始, l从l_2 开始a = cat(1,[0],a); % a = [0, diag(A,-1)]u = zeros(1,n);l = zeros(1,n);u(1) = b(1);for i = 2:1:nl(i) = a(i)/u(i-1);u(i) = b(i)-l(i)*c(i-1);end% Ly = by = zeros(1,n);y(1) = f(1);for i =2:1:ny(i) = f(i)-l(i)*y(i-1);end% Ux= yx = zeros(n,1);x(n) = y(n)/u(n);for i =n-1:-1:1x(i) = (y(i) - c(i)* x(i+1))/u(i);end
end
保存为 tridiag_chase.m
文件
简单测试一下
在 10、100、500 、1000阶 三对角方程组下, 追赶法与gauss列主元消去法 的时间消耗对比
% file need: tridiag_chase.m, gsem_column.m
% time: 1/26/2024
%%
clc,clear all;
n = 10; % 方程组的阶数 10 100 500 1000
A = diag(2*ones(n,1)) + diag(-1*ones(n-1,1),1) + diag(-1*ones(n-1,1),-1);
f = (1:n)';
t1 = tic;
x1 = tridiag_chase(A,f);
toc(t1);t2 = tic;
x2 = gsem_column(A,f);
toc(t2);delta = norm(abs(x1-x2));
n | 追赶法 | Gauss列主元 | delta |
---|---|---|---|
10 | 0.242069 s | 0.253921 s | 0 |
100 | 0.249970 s | 0.997883 s | 0 |
500 | 0.373002 s | 19.068616 s | 0 |
1000 | 0.440046 s | 81.370982 s | 0 |
随着方程组阶数的增大、其优势愈加明显。
其中用到的 Gauss列主元消去法 ,见左方蓝色字体。