3、PCA in 2D
做这个实验对于PCA有了进一步的了解,但是其实还是没有完全理解。不过先就这样了。
- 问题:
1)其实对于PCA这块还是没有比较深刻的理解
2)SVD不懂呀。
3)
4)
5)
- 想法:
1)感觉,如果PCA只是为了降维准备的话,应该还是要按照Andrew Ng CS229中的方法,先0均值,然后标准方差,然后PCA,这套流程比较好。
2)这个实验其实,没有做0均值处理,主要是实验第一步,要在原始数据中,画出主成分方向,所以后面就直接调用前面的计算的数据了。但是算了一个原始数据的均值,分别为0.0185 0.0318,所以其实0均值意义不大,可能也符合UFLDL总所说的:PCA算法正常工作的两个前提:1、特征的均值大致为0;2、不同特征的方差值彼此相似。
3)
4)
5)
这实验需要下载pca_2d.zip,然后里面只有一个程序pca_2d.m,和数据pcaData.txt。由于对于PCA理解不到位,自己也在后面画了一些对比图。方便自己理解。
pca_2d.m
close all;clc;clear; %%================================================================ %% Step 0: Load data % We have provided the code to load data from pcaData.txt into x. % x is a 2 * 45 matrix, where the kth column x(:,k) corresponds to % the kth data point.Here we provide the code to load natural image data into x. % You do not need to change the code below. x = load('pcaData.txt','-ascii'); figure(1); scatter(x(1, :), x(2, :)); title('Raw data'); %%================================================================ %% Step 1a: Implement PCA to obtain U % Implement PCA to obtain the rotation matrix U, which is the % eigenbasis特征向量 % sigma. % -------------------- YOUR CODE HERE -------------------- u = zeros(size(x, 1)); % You need to compute this %由于这个代码,主要是想在原始数据的图像上,画出主要变化方向。 %所以就直接在原始数据上进行操作。 %做这个才发现了之前对于PCA理解上面的缺陷,其实PCA一般要先进行0均值和单位方差的操作 %但其实0均值和单位方差的操作的主要目的是规范化数据不同的维度可能存在的量级上面的差异 %在原始数据的协方差矩阵进行操作,就可以找到主特征方向。 %这一小段程序,就说明了这个问题。 % sigma=x*x'/size(x,2); [u,s,v]=svd(sigma); % -------------------------------------------------------- hold on plot([0 u(1,1)], [0 u(2,1)]); plot([0 u(1,2)], [0 u(2,2)]); scatter(x(1, :), x(2, :)); hold off set(gcf,'NumberTitle','off'); set(gcf,'Name','1、原始数据中画出主成分方向'); %%================================================================ %% Step 1b: Compute xRot, the projection on to the eigenbasis % Now, compute xRot by projecting the data on to the basis defined % by U. Visualize the points by performing a scatter plot. % -------------------- YOUR CODE HERE -------------------- xRot = zeros(size(x)); % You need to compute this xRot = u'*x; % -------------------------------------------------------- % Visualise the covariance matrix. You should see a line across the % diagonal against a blue background. figure(2); scatter(xRot(1, :), xRot(2, :)); title('xRot'); set(gcf,'NumberTitle','off'); set(gcf,'Name','2、原始数据按主成分方向翻转后的数据'); %%================================================================ %% Step 2: Reduce the number of dimensions from 2 to 1. % Compute xRot again (this time projecting to 1 dimension). % Then, compute xHat by projecting the xRot back onto the original axes % to see the effect of dimension reduction % -------------------- YOUR CODE HERE -------------------- k = 1; % Use k = 1 and project the data onto the first eigenbasis xHat = zeros(size(x)); % You need to compute this % xHat = u'*[xRot(1:k,:);zeros(1,size(xRot,2))];%按照公式去前k维 % 下面为按照完整的公式得到的式子 xHat = u'*([u(:,1:k),zeros(size(u,1),1)]'*x); % -------------------------------------------------------- figure(3); scatter(xHat(1, :), xHat(2, :)); title('xHat'); set(gcf,'NumberTitle','off'); set(gcf,'Name','3、原始数据投影到第一个主成分上的数据'); %%================================================================ %% Step 3: PCA Whitening % Complute xPCAWhite and plot the results. epsilon = 1e-5; % -------------------- YOUR CODE HERE -------------------- xPCAWhite = zeros(size(x)); % You need to compute this xPCAWhite = diag(1./sqrt(diag(s)+epsilon))*xRot; %由于要对应维度上都要除以特征值,只能用乘法 % xPCAWhite = diag(1./sqrt(diag(s)+epsilon))*u'*x; % -------------------------------------------------------- figure(4); scatter(xPCAWhite(1, :), xPCAWhite(2, :)); title('xPCAWhite'); set(gcf,'NumberTitle','off'); set(gcf,'Name','4、PCAwhite后数据(主成分翻转数据,然后归一化各个维度方差)'); %%================================================================ %% Step 3: ZCA Whitening % Complute xZCAWhite and plot the results. % -------------------- YOUR CODE HERE -------------------- xZCAWhite = zeros(size(x)); % You need to compute this % xZCAWhite=u*xPCAWhite; xZCAWhite=u*diag(1./sqrt(diag(s)+epsilon))*u'*x; % -------------------------------------------------------- figure(5); scatter(xZCAWhite(1, :), xZCAWhite(2, :)); title('xZCAWhite'); set(gcf,'NumberTitle','off'); set(gcf,'Name','5、ZCAwhite后数据(PCAwhite后翻转回原来的方向)'); %% Congratulations! When you have reached this point, you are done! % You can now move onto the next PCA exercise. :) %下面是由于对于PCA的原理还有些疑惑,所以添加的对比图像。 %对比以下图像能够更加容易的理解这个实验。 ysWhite=diag(1./sqrt(diag(s)+epsilon))*x; figure(6); scatter(ysWhite(1, :), ysWhite(2, :)); set(gcf,'NumberTitle','off'); set(gcf,'Name','6、原始数据做奇异值规整化'); figure(7); % xRot = u'*x; scatter(xRot(1, :), zeros(1, size(xRot,2))); set(gcf,'NumberTitle','off'); set(gcf,'Name','7、原始数据主成分翻转数据,投影到翻转后数据的第一个维度'); figure(8); fzhy=u'*u*x; scatter(fzhy(1, :), fzhy(2, :)); set(gcf,'NumberTitle','off'); set(gcf,'Name','8、原始数据按主成分方向,翻转回原始数据');
实验结果:
1、原始数据画出主成分方向。8、翻转两次后图像就转换到原始数据。
3、原始数据投影到第一个主成分方向。
2、原始数据按照主成分翻转后的数据。7、翻转后图像,投影到第一个维度,一般做PCA降维后应该都是这样的结果。
4、PCAwhite(翻转后的数据,规整化各个维度的方差)。
5、ZCAwhite(PCAwhite后的数据翻转回原始坐标)
6、原始数据,做奇异值规整化。