跳轉到

6.4 對稱矩陣與譜定理#

本節目標#

  • 認識對稱矩陣 \(A = A^T\) 的特殊性:它是一般矩陣中的「乖寶寶」
  • 學會譜定理:對稱矩陣必有實特徵值與正交特徵基,即 \(A = Q\Lambda Q^T\)
  • 用 np.linalg.eigh(比 eig 更穩更快)做特徵分解
  • 從幾何理解:對稱矩陣沿特徵方向只伸縮、不旋轉
  • 實驗:對稱 vs 非對稱特徵值對照、二次型 \(\mathbf{x}^T A\mathbf{x}\) 與正定的初步直覺

對稱矩陣:向自己對稱的矩陣#

把矩陣沿主對角線「翻面」,如果還是自己,就是對稱矩陣:

\[ A = \begin{bmatrix} 2 & 1 \\ 1 & 3 \end{bmatrix} = A^T \]

哪裡會遇到它?出乎意料地常見:

  • 資料的協方差矩陣(第 \(i\) 行第 \(j\) 列 = 變數 \(i\) 與 \(j\) 的共變,當然對稱)
  • 圖的鄰接矩陣(友誼是互相的, \(a_{ij} = a_{ji}\) )
  • 內積矩陣、彈簧系統的能量矩陣、二次型
  • 任何 \(B^T B\) 或 \(B B^T\) (例如最小平方法的 \(A^T A\) !)
import numpy as np

B = np.random.randn(4, 3)
S = B.T @ B           # 永遠對稱
print(np.allclose(S, S.T))   # True

譜定理:對稱矩陣必可正交對角化#

一般矩陣的特徵值可能不存在(複數)、特徵向量可能不夠用(第 8 章的瑕疵矩陣)。 但對稱矩陣有整套保證,這就是譜定理(spectral theorem):

若 \(A = A^T\) ,則 1. 所有特徵值都是實數 2. 存在一組互相垂直的特徵向量,湊成完整的 orthonormal 基 3. 因此 \(A\) 可以寫成

\[ > A = Q \Lambda Q^T, \qquad > Q = \begin{bmatrix} \mathbf{q}_1 & \cdots & \mathbf{q}_n \end{bmatrix} \text{(正交)}, \quad > \Lambda = \text{diag}(\lambda_1, \dots, \lambda_n) > \]

注意 \(Q^{-1} = Q^T\) ,所以反矩陣免費:

\[ A = Q\Lambda Q^T \;\Longleftrightarrow\; A^{-1} = Q\Lambda^{-1}Q^T, \qquad \mathbf{x} = Q\Lambda^{-1}Q^T\mathbf{b} \]

特徵值像矩陣的「光譜」——把變換 \(A\) 拆成 \(n\) 個純粹的伸縮動作, 沿著一組互相垂直的軸各自放大 \(\lambda_i\) 倍。


用 np.linalg.eigh#

對稱矩陣請用專屬的 eigh,不要用一般性的 eig:

import numpy as np

A = np.array([[2., 1.],
              [1., 3.]])

w, Q = np.linalg.eigh(A)   # w = 特徵值(已排序),Q = 正交特徵向量
print(w)                   # 實數,且由小到大
print(Q)                   # orthonormal

# 驗證 A = Q Λ Q^T
print(Q @ np.diag(w) @ Q.T)
print(np.allclose(Q.T @ Q, np.eye(2)))   # Q 真的是正交矩陣
eig eigh
適用對象 任意方陣 對稱(Hermitian)矩陣
速度 較慢 快約 2~3 倍
穩定性 較低 較高(利用對稱性)
特徵值 可能有複數虛部 保證實數、已排序

eigh 直接利用你「知道矩陣對稱」這個資訊,所以更快更穩。 程式設計的教訓:能給演算法的結構資訊就別藏。


幾何:只伸縮、不旋轉#

回憶 3 章:一般矩陣作用在向量上,常常旋轉 + 伸縮同時發生。 但對稱矩陣沿著特徵方向 \(\mathbf{q}_i\) ,動作是純伸縮:

\[ A\mathbf{q}_i = \lambda_i \mathbf{q}_i \]

方向完全不轉,只拉長或縮短 \(\lambda_i\) 倍。任意向量呢?先用 \(Q^T\) 換到特徵座標、 逐軸伸縮、再轉回來:

\[ A\mathbf{v} = Q\Lambda Q^T\mathbf{v} \quad=\quad \underbrace{Q}_{\text{轉入特徵座標}} \; \underbrace{\Lambda}_{\text{純伸縮}} \; \underbrace{Q^T}_{\text{轉回原座標}} \]
import numpy as np
from linalg_viz import plot_vectors

A = np.array([[2., 1.],
              [1., 3.]])

w, Q = np.linalg.eigh(A)
q1, q2 = Q[:, 0], Q[:, 1]

# 特徵方向上的向量:只變長度,方向不變
print(A @ q1, w[0] * q1)   # 相同
print(A @ q2, w[1] * q2)   # 相同

# 畫圖:灰箭頭是原向量,彩箭頭是 A v,特徵方向以虛線標示
plot_vectors([q1, q2], labels=['q1', 'q2'], color='gray')
plot_vectors([A @ q1, A @ q2], labels=['A q1', 'A q2'])

畫圖會看到: \(A\mathbf{q}_1\) 與 \(\mathbf{q}_1\) 在同一條線上( \(\lambda_1 < 0\) 時反向), \(A\mathbf{q}_2\) 同理,而且兩組箭頭保持垂直。


實驗一:對稱 vs 非對稱的特徵值#

import numpy as np

np.random.seed(1)
B = np.random.randn(5, 5)
S = (B + B.T) / 2          # 任意矩陣對稱化

print("對稱矩陣特徵值:")
print(np.linalg.eigvalsh(S))          # 全是實數

print("非對稱矩陣特徵值:")
w = np.linalg.eigvals(B)
print(w)                               # 帶 ± 虛部(複數)!

print("非對稱矩陣的特徵向量正交嗎?")
w, V = np.linalg.eig(B)
V = V.real
print(np.abs(V.T @ V - np.eye(5)).max())   # 通常遠離 0

對照結果非常清楚:非對稱矩陣的特徵值常帶虛部,特徵向量也不正交; 對稱矩陣兩者都乖——這正是譜定理承諾的。


實驗二:二次型 \(\mathbf{x}^T A\mathbf{x}\) 與正定的初步直覺#

把矩陣夾在一個向量的兩側: \(f(\mathbf{x}) = \mathbf{x}^T A\mathbf{x}\) ,這是二次型。 例如 \(A = \begin{bmatrix} 2 & 1 \\ 1 & 3 \end{bmatrix}\) 時:

\[ \mathbf{x}^T A\mathbf{x} = 2x_1^2 + 2x_1 x_2 + 3x_2^2 \]

它是「向量 \(\mathbf{x}\) 在 \(A\) 這把尺下的能量」。在特徵座標下超級簡單:

\[ \mathbf{x} = Q\mathbf{y} \;\Longrightarrow\; \mathbf{x}^T A\mathbf{x} = \mathbf{y}^T \Lambda \mathbf{y} = \lambda_1 y_1^2 + \lambda_2 y_2^2 \]

所有特徵值 \(> 0\) (正定)時,這個值對任何 \(\mathbf{x} \neq \mathbf{0}\) 都 \(> 0\) —— 碗狀的能量面,唯一的最小值在原點。這就是二次函數有唯一最小值、 高斯消去不會翻車的代數保證(也呼應 6.3: \(A^T A\) 永遠半正定)。

import numpy as np
import matplotlib.pyplot as plt

A = np.array([[2., 1.],
              [1., 3.]])
print(np.linalg.eigvalsh(A))   # 都 > 0 → 正定

# 畫 z = x^T A x 的能量面:正定 → 碗狀
g = np.linspace(-2, 2, 100)
X, Y = np.meshgrid(g, g)
Z = 2*X**2 + 2*X*Y + 3*Y**2

plt.contourf(X, Y, Z, levels=30, cmap='viridis')
plt.colorbar(label='x^T A x')
plt.title("正定矩陣的二次型:橢圓等高線的碗")
plt.gca().set_aspect('equal')
plt.show()

# 反例:有一個負特徵值 → 馬鞍面
B = np.array([[1., 0.],
              [0., -1.]])
Z2 = X**2 - Y**2
plt.contourf(X, Y, Z2, levels=30, cmap='coolwarm')
plt.title("有負特徵值:馬鞍,某些方向是「下坡」")
plt.gca().set_aspect('equal')
plt.show()

讀圖要點:等高線是橢圓還是雙曲線,完全由特徵值的正負號決定; 橢圓的長短軸方向,正是特徵向量的方向。特徵值不只是數字,是能量面的形狀密碼。


小結與練習#

本節重點 1. 對稱矩陣 \(A = A^T\) 隨處可見:協方差、鄰接矩陣、 \(A^T A\) 、二次型。 2. 譜定理:對稱矩陣必有實特徵值與正交特徵基, \(A = Q\Lambda Q^T\) ,反矩陣免費。 3. 對稱矩陣沿特徵方向純伸縮不旋轉;幾何動作 = 轉入特徵座標 → 伸縮 → 轉回。 4. 用 eigh 而非 eig:更快、更穩、特徵值自動排序。 5. 特徵值的正負決定二次型 \(\mathbf{x}^T A\mathbf{x}\) 是碗還是馬鞍——「正定」的初步直覺。

練習 1. 對 \(A = \begin{bmatrix} 4 & 2 \\ 2 & 1 \end{bmatrix}\) 用 eigh 分解,並驗證 \(A = Q\Lambda Q^T\) 與 \(Q^TQ = I\) 。 2. 把實驗二的 \(A\) 換成 \(\begin{bmatrix} 1 & 2 \\ 2 & 1 \end{bmatrix}\) ,先判斷正定性,再畫圖驗證你的判斷。 3. 挑戰:對非對稱矩陣 \(B\) ,計算 \(S = \frac{B + B^T}{2}\) 的 eigh 分解,思考——對稱部分捕捉了 \(B\) 的哪些行為?(提示:反對稱部分只負責旋轉,第 8 章見分曉。)