function [inertia,casecoord,varcoord]=genpca(data,varargin) % PURPOSE : Generalized pca implementation %--------------------------------------------------------------------------- % USAGE : [inertia,casecoord,varcoord]=genpca(data,weight,metric,center,reduc) % where : data : (n x p) data matrix % weight : optional (n x 1) weight vector. The default is weight=(1/n,...,1/n)'. % metric : optional (p x p) matrix. The default is the identity matrix. % center : optional boolean: if center=1 : the pca is centered (default). % if center=0 : the pca is not centered. % reduc : optional boolean: if reduc=1 : the pca is standardized (default). % if reduc=0 : the pca is not standardized. %----------------------------------------------------------------------------- % OUTPUTS : Inertia : (p x 1) vector of inertia % casecoord : (n x p) matrix containing the case coordinates (principal components) % varcoord : (p x p) matrix containing the variables coordinates %----------------------------------------------------------------------------- % used in pcamap.m %------------------------------------------------------------------------ % Anne Ruiz-Gazen, Julien Moutel % June 2003 % Université de Toulouse I, Toulouse, France % cthomas@cict.fr x=data; w=ones(size(data,1),1)/size(data,1); m=eye(size(data,2)); center=1; reduc=1; if ~isempty(varargin) t=size(varargin,2); if ~isempty(varargin{1}) w=varargin{1}; end; if t>=2 & ~isempty(varargin{2}) m=varargin{2}; end; if t>=3 & ~isempty(varargin{3}) center=varargin{3}; end; if t==4 & ~isempty(varargin{4}) reduc=varargin{4}; end; end; w=w/sum(w); W=diag(w); xbar=sum(repmat(w,1,size(data,2)).*data)'; if center==1 xc=x-ones(size(x,1),1)*xbar'; else xc=x; end; sig2=sum(repmat(w,1,size(x,2)).*(x.^2))'-xbar.^2; sigma=(size(x,1)/(size(x,1)-1))*diag(sig2); sigmademi=sqrt(((size(x,1)-1)/size(x,1)))*diag(sig2.^(-1/2)); if reduc==1 xcr=xc*sigmademi; else xcr=xc; end; cov=xcr'*W*xcr; l=chol(m); covn=l*cov*l'; [U,D]=eigs(covn); V=l'*U; casecoord=xcr*V; Dv=diag(D); Dvdemi=Dv.^(-1/2); Ddemi=diag(Dvdemi); varcoord=cov*V*Ddemi; inertia=Dv;