1. 概念

2. 作用
把前K个比较大的奇异值保留,其余设为0,得到Σ',由UΣ'VT得到A',其保留了A的主要信息,去掉可能存在的噪声,即不重要的信息。
有助于建模,且有可能用其去选择更合适的特征,以及可以应用于隐特征的挖掘。
比如:上述公式中U可以表示为用户信息,VT可以表示为商品特征,印刻可以用于商品的推荐。
3. 步骤
求ATA的特征值和特征向量(可以用QR分解,np.linalg.eig())
特征向量归一化后为右奇异向量V
特征值开方为奇异值
根据Av1 = 奇异值1 * u1,依次得到左奇异向量ui
4. 代码实现
#!/usr/bin/python
# -*- coding:utf-8 -*-
import numpy as np
import os
np.set_printoptions(linewidth = 200)
np.random.seed(14)
A = np.random.randn(4,5).reshape(4,5)
print("原始矩阵A(4*5):\n", A)
X = A.T.dot(A)
print("原始矩阵的转置与其本身矩阵相乘得到矩阵X = A^T*A:\n", X)
eig_value,eig_vector = np.linalg.eig(X)
print("矩阵X的特征值为:\n", eig_value)
print("矩阵X的特征向量为:\n", eig_vector) # 每一列为一个特征向量
sigma = np.sqrt(eig_value)
v = eig_vector
sigma_mat = np.zeros(X.shape)
for i in np.arange(sigma.shape[0]):
sigma_mat[i,i] = sigma[i]
av = A.dot(v)
#u = av.dot(np.mat(sigma_mat).I)
u = av / sigma
A_calc = (u * sigma).dot(v.T) # 用通过求解的特征值和特征向量来得到原始的矩阵A
print("原始矩阵A:\n", A)
print("通过求解特征值和特征向量,将其带入SVD公式,得到的原始矩A':\n", A_calc)
print("二者的差值:\n", A - A_calc)
print("二者是否相等:\n", np.allclose(A, A_calc))
print("通过调用np的SVD库,得到矩阵A的左右奇异向量和奇异值")
u1,s1,vt1 = np.linalg.svd(A, full_matrices = False)
A_svd = (u1 * s1).dot(vt1)
print("原始矩阵A:\n", A)
print("通过SVD求解左右奇异值和奇异向量,得到的原始矩A':\n", A_svd)
print("二者的差值:\n", A - A_svd)
print("二者是否相等:\n", np.allclose(A, A_svd))
更多文章请关注《万象专栏》
转载请注明出处:https://www.wanxiangsucai.com/read/cv80186