【机器学习】Matlab_主成份分析(PCA)
写在前面:本文根据自己数据挖掘的课程作业整理,结合吴恩达机器学习的课程。
作业中的算法描述:
试使用MATLAB 中的svd 函数实现PCA 算法,即输入数据矩阵X 和降维后的维数k,对每一个样本进行去中心化,然后对进行去中心化后的数据矩阵Xc 用svd 函数[U,S,V] = svd(Xc),输出降维的投影矩阵Ureduce(即U 的前k 列),降维后的坐标表示Z=Ureduce’*Xc。
因为使用Matlab中的eig也同样能够达到计算特征值和特征向量的目的,所以代码中实现了两种方法,并使用yale_face数据集作为测试。
test.m:
clear;
load('yale_face.mat');
[n, m]= size(X);
imshow(reshape(X(:,1),[64,64]),[]);
for i= 1:3
subplot(3,1,i)
imshow(reshape(X(:,i),[64,64]),[]);
end
%[Z1, V1]= mPCA(X, 5);
% [U2_reduce, Z2, V2]= mPCA(X, 10);
% X_re2= U2_reduce* Z2;
% for i= 1:3
% subplot(3,1,i)
% imshow(reshape(X_re2(:,i),[64,64]),[]);
% end
[U3_reduce, Z3, V3]= mPCA(X, 100);
X_re3= U3_reduce* Z3;
for i= 1:3
subplot(3,1,i)
imshow(reshape(X_re3(:,i),[64,64]),[]);
end
算法核心mPCA.m:
function [ U_reduce, z, V_retain ] = mPCA( X, k )
% 算法输入特征X和降维后的维度k,输入降维后的矩阵z和保留的方差比例V_retain和U_reduce
[n, m]= size(X);
% 得到均值,保存均值图像
u= mean(X');
%imshow(reshape(u,[64,64]),[]);
%imwrite(uint8(reshape(u, [64,64])),'u.png');
% 去中心化
u= u'
mu= repmat(u, 1, m);
X_mu= X-mu;
%SVD
tic
[U1, S, V]= svd(X_mu);
toc
% 得到U_reduce
U_reduce= U1(:,1:k);
% 计算保留的方差比例
d= diag(S).^2;
V_retain= sum(d(1:k))/ sum(d(1:m));
% 显示前5个结果
for i= 1:5
subplot(k,1,i)
imshow(reshape(U_reduce(:,i),[64,64]),[]);
end
% %eig
% sigma= (1/m)* (X_mu* X_mu');
% tic
% [U2, D]= eig(sigma);
% toc
%
% U_reduce= U2(:,end- k+ 1:end);
%
% d= diag(D);
% V_retain= sum(d(1:k))/ sum(d(1:m));
%
% for i= 1:k
% subplot(k,1,i)
% imshow(reshape(U_reduce(:,i),[64,64]),[]);
% end
% 得到降维后的结果z
z= U_reduce'* X_mu;
end
值得注意的是,svd是直接使用去中心化后的矩阵的,与吴恩达课程课件不同。而eig使用的是sigma函数。