wolffd@0: function [evals, evec] = eigdec(x, N) wolffd@0: %EIGDEC Sorted eigendecomposition wolffd@0: % wolffd@0: % Description wolffd@0: % EVALS = EIGDEC(X, N computes the largest N eigenvalues of the wolffd@0: % matrix X in descending order. [EVALS, EVEC] = EIGDEC(X, N) also wolffd@0: % computes the corresponding eigenvectors. wolffd@0: % wolffd@0: % See also wolffd@0: % PCA, PPCA wolffd@0: % wolffd@0: wolffd@0: % Copyright (c) Ian T Nabney (1996-2001) wolffd@0: wolffd@0: if nargout == 1 wolffd@0: evals_only = logical(1); wolffd@0: else wolffd@0: evals_only = logical(0); wolffd@0: end wolffd@0: wolffd@0: if N ~= round(N) | N < 1 | N > size(x, 2) wolffd@0: error('Number of PCs must be integer, >0, < dim'); wolffd@0: end wolffd@0: wolffd@0: % Find the eigenvalues of the data covariance matrix wolffd@0: if evals_only wolffd@0: % Use eig function as always more efficient than eigs here wolffd@0: temp_evals = eig(x); wolffd@0: else wolffd@0: % Use eig function unless fraction of eigenvalues required is tiny wolffd@0: if (N/size(x, 2)) > 0.04 wolffd@0: fprintf('netlab pca: using eig\n'); wolffd@0: [temp_evec, temp_evals] = eig(x); wolffd@0: else wolffd@0: options.disp = 0; wolffd@0: fprintf('netlab pca: using eigs\n'); wolffd@0: [temp_evec, temp_evals] = eigs(x, N, 'LM', options); wolffd@0: end wolffd@0: temp_evals = diag(temp_evals); wolffd@0: end wolffd@0: wolffd@0: % Eigenvalues nearly always returned in descending order, but just wolffd@0: % to make sure..... wolffd@0: [evals perm] = sort(-temp_evals); wolffd@0: evals = -evals(1:N); wolffd@0: %evec=temp_evec(:,1:N); wolffd@0: if ~evals_only wolffd@0: if evals == temp_evals(1:N) wolffd@0: % Originals were in order wolffd@0: evec = temp_evec(:, 1:N); wolffd@0: return wolffd@0: else wolffd@0: fprintf('netlab pca: sorting evec\n'); wolffd@0: % Need to reorder the eigenvectors wolffd@0: for i=1:N wolffd@0: evec(:,i) = temp_evec(:,perm(i)); wolffd@0: end wolffd@0: end wolffd@0: end