0

I'm doing PCA on my data using MATLAB and want to make a 3D PCA plot with 95% ellipsoids for each category. My code is as follows:

% Input data
InputData = [7.72 6.73 3.33 0.12 0.06 -0.31 1;
             8.92 8.22 4.56 0.06 0.72 0.01 1;
             2.11 1.59 0.7 0.12 0.67 -0.02 1;
             79.42 92.88 75.03 64.98 67.8 55.93 2;
             100.82 112.5 94.7 73.16 74.22 64.15 2;
             69.43 83.4 67.46 80.78 81.36 69.38 2;
             25.25 23.86 17.95 0.12 0.44 0.14 3;
             39.97 36.9 30.06 0.13 0.82 0.35 3;
             31.99 29.48 23.68 -0.12 0.53 -0.1 3;
             129.93 126.54 113.51 1.09 0.17 0.38 4;
             129.91 127.4 114.6 1.32 1.05 1.19 4;
             110.38 108.7 96.3 0.41 1.25 0.87 4];

% Extract the features (first 6 columns) and labels (last column) from the data
X = InputData(:,1:6);
labels = InputData(:,7);

% Perform PCA on the data
[coeff,score,latent,~,explained] = pca(X);

% Get the first three principal components
PC1 = score(:,1);
PC2 = score(:,2);
PC3 = score(:,3);

% Calculate the means for each label
mean1 = mean(score(labels==1,1:3));
mean2 = mean(score(labels==2,1:3));
mean3 = mean(score(labels==3,1:3));
mean4 = mean(score(labels==4,1:3));

% Calculate the covariance matrices for each label
cov1 = cov(score(labels==1,1:3));
cov2 = cov(score(labels==2,1:3));
cov3 = cov(score(labels==3,1:3));
cov4 = cov(score(labels==4,1:3));

% Set the confidence level for the ellipsoids
confLevel = 0.95;

% Create a 3D scatter plot with different colors for each label
figure
scatter3(PC1(labels==1), PC2(labels==1), PC3(labels==1), 'r', 'filled')
hold on
scatter3(PC1(labels==2), PC2(labels==2), PC3(labels==2), 'g', 'filled')
scatter3(PC1(labels==3), PC2(labels==3), PC3(labels==3), 'b', 'filled')
scatter3(PC1(labels==4), PC2(labels==4), PC3(labels==4), 'm', 'filled')
title('3D Scatter Plot with 95% Confidence Ellipsoids')
xlabel('PC1')
ylabel('PC2')
zlabel('PC3')
legend('Label 1', 'Label 2', 'Label 3', 'Label 4')

% Create the ellipsoids for each label
drawEllipsoid(mean1, cov1, confLevel, 'r')
drawEllipsoid(mean2, cov2, confLevel, 'g')
drawEllipsoid(mean3, cov3, confLevel, 'b')
drawEllipsoid(mean4, cov4, confLevel, 'm')

% Function to draw ellipsoids
function drawEllipsoid(mn, covMatrix, confLevel, color)
    % Get the eigenvalues and eigenvectors of the covariance matrix
    [V,D] = eig(covMatrix);

    % Calculate the radii of the ellipsoid
    radii = sqrt(abs(diag(D)) * finv(confLevel, 3, size(mn,2)-1));

    % Generate points on a unit sphere
    [x,y,z] = sphere(20);

    % Transform the points using the eigenvectors and radii
    pnts1 = [x(:) y(:) z(:)];
    pnts = [x(:) y(:) z(:)] * V * diag(radii);

    % Add the mean to the points
    pnts = bsxfun(@plus, pnts, mn);

    % Reshape the points into a matrix
    F1 = reshape(pnts(:,1), size(x,1), size(x,2));
    F2 = reshape(pnts(:,2), size(x,1), size(x,2));
    F3 = reshape(pnts(:,3), size(x,1), size(x,2));

    % Plot the ellipsoid
    mesh(F1,F2,F3, 'EdgeColor', color, 'FaceAlpha', 0.1, 'EdgeAlpha', 0.1)
    hold on
end

It yields the following plot: enter image description here

As you can see, the ellipsoids turn out to be ellipses (2D), not 3D. Can someone explain and/or show how to fix it?

Notes: I'm using abs function to get the radii because it was giving me complex numbers. The code runs with no warnings or errors.

STEMQs
  • 75
  • 1
  • 10
  • For each class you have 3 data points in 6 dimensions. That is not enough to do anything with. You cannot do more than fit a 2D surface to the three points. – Cris Luengo May 02 '23 at 21:36
  • @CrisLuengo can you explain the reasoning (mathematical or intuitive) for that? – STEMQs May 03 '23 at 13:50
  • 1
    To fit a circle in 2D you need at least 3 points, with fewer points there’s information missing, many different circles fit two points. To fit a ball in 3D you need at least 4 points. With each dimension you add you need one more point. So, in 6D, you’d need 7 points to fit a ball. You have only 3 points, so the best PCA can do is fit a 2D shape. There’s not enough information to find a higher-dimensional shape. – Cris Luengo May 03 '23 at 13:54
  • @CrisLuengo got it! So based on the explanation, I added 1 more point (for a total of 4) and ran that on my code. I still had 2D ellipses, not ellipsoids. – STEMQs May 03 '23 at 14:11

0 Answers0