正交化,简单地说,就是指把若干向量转化成互相之间夹角为90度的状态,这样互相之间没有影响。否则,不满足正交性的因子,相互会影响各自的回归系数,从而可能导致回归系数过大等估计误差,从而影响该因子的评价。
这里讨论最常见的施密特正交化。

1、施密特正交化的几何解释

给定一组基α1,α2,…,αn,将其变换成另外一组正交基β1,β2,…,βn,使这两组基等价

施密特正交化方法:

如何生成两两正交的向量python 怎么将两个向量正交化_如何生成两两正交的向量python

1)在二维的情况下

此时有两个向量α、β,其中 α 在 β 上的投影向量为

如何生成两两正交的向量python 怎么将两个向量正交化_python_02

如图红色部分即为投影部分

如何生成两两正交的向量python 怎么将两个向量正交化_python_03


则蓝色部分向量为

如何生成两两正交的向量python 怎么将两个向量正交化_python_04


对应两个向量的施密特法则

如何生成两两正交的向量python 怎么将两个向量正交化_如何生成两两正交的向量python_05

可见蓝色向量 β2 与β1是垂直的。
以上公式也可以推算得到。
先令向量 β1 = α1,只要找到另外一个新的向量 β2,使得 β2 与 β1 内积为0,这两个向量就是正交的了。如何寻找?

根据向量之间的运算关系,因为 β2 由 β1、α2 得到,则我们可以设
如何生成两两正交的向量python 怎么将两个向量正交化_python_06
因为 β2 与 β1 内积为0,因此
如何生成两两正交的向量python 怎么将两个向量正交化_如何生成两两正交的向量python_07
则有
如何生成两两正交的向量python 怎么将两个向量正交化_如何生成两两正交的向量python_08
如何生成两两正交的向量python 怎么将两个向量正交化_python_09
因此
如何生成两两正交的向量python 怎么将两个向量正交化_线性代数_10
令 k = 1,就得到了新的正交向量 如何生成两两正交的向量python 怎么将两个向量正交化_python_11如何生成两两正交的向量python 怎么将两个向量正交化_如何生成两两正交的向量python_12

举个栗子(没看错,是举着栗子。。。),现有矩阵 [a, b]
如何生成两两正交的向量python 怎么将两个向量正交化_线性代数_13如何生成两两正交的向量python 怎么将两个向量正交化_二维_14

根据以上公式有:
A = a
如何生成两两正交的向量python 怎么将两个向量正交化_二维_15
代入具体数值,有
如何生成两两正交的向量python 怎么将两个向量正交化_二维_16
如何生成两两正交的向量python 怎么将两个向量正交化_二维_17

2)在三维的情况下

即向量个数为3时,对应三维空间的几何解释如图 。

如何生成两两正交的向量python 怎么将两个向量正交化_二维_18


其中绿色的为需要正交的原始基αi(α1是红色的因为α1同时也是β1)

将二维得到的β2平移到坐标原点出后则α3在xoy平面的投影即是

如何生成两两正交的向量python 怎么将两个向量正交化_二维_19


即α3在β1和β2上的投影组成的平行四边形的斜边,则得到的β3就是α3与该投影的向量差,即红色部分的β3,显然可以看出来β1,β2,β3是正交的。

从推算的角度,我们可以令
如何生成两两正交的向量python 怎么将两个向量正交化_如何生成两两正交的向量python_20
要让如何生成两两正交的向量python 怎么将两个向量正交化_python_21,需要
如何生成两两正交的向量python 怎么将两个向量正交化_二维_22

如何生成两两正交的向量python 怎么将两个向量正交化_二维_23

要让如何生成两两正交的向量python 怎么将两个向量正交化_python_24,需要
如何生成两两正交的向量python 怎么将两个向量正交化_如何生成两两正交的向量python_25

如何生成两两正交的向量python 怎么将两个向量正交化_二维_26
因此
如何生成两两正交的向量python 怎么将两个向量正交化_python_27

三维以上空间里的公式以此类推。

2、代码实现

import numpy as np
A = np.array([[1,1,0],[0,1,1],[1,0,1]],dtype=float)
Q = np.zeros_like(A)
m, n = Q.shape
cnt = 0
for a in A.T:
    u = np.copy(a)
    for i in range(0, cnt):
        u -= np.dot(np.dot(Q[:, i].T, a), Q[:, i]) # 减去待求向量在以求向量上的投影
    e = u / np.linalg.norm(u)  # 归一化
    Q[:, cnt] = e
    cnt += 1
print(Q)

或者

from scipy import linalg
A = np.array([[1,1,0],[0,1,1],[1,0,1]])
a = linalg.orth(A)
print(np.array(linalg.orth(A),dtype=float))
print(np.dot(A,A.T)-1)

参考: 揭秘施密特正交化