annotate util/classes/dictionaryMatrices/grassmannian.m @ 160:e3035d45d014 danieleb

Added support classes
author Daniele Barchiesi <daniele.barchiesi@eecs.qmul.ac.uk>
date Wed, 31 Aug 2011 10:53:10 +0100
parents
children 88578ec2f94a
rev   line source
daniele@160 1 function [A G res muMin] = grassmannian(n,m,nIter,dd1,dd2,initA,verb)
daniele@160 2 % grassmanian attempts to create an n by m matrix with minimal mutual
daniele@160 3 % coherence using an iterative projection method.
daniele@160 4 %
daniele@160 5 % [A G res] = grassmanian(n,m,nIter,dd1,dd2,initA)
daniele@160 6 %
daniele@160 7 %
daniele@160 8 %% Parameters and Defaults
daniele@160 9 error(nargchk(2,7,nargin));
daniele@160 10
daniele@160 11 if ~exist('verb','var') || isempty(verb), verb = false; end %verbose output
daniele@160 12 if ~exist('initA','var') || isempty(initA), initA = randn(n,m); end %initial matrix
daniele@160 13 if ~exist('dd2','var') || isempty(dd2), dd2 = 0.95; end %shrinking factor
daniele@160 14 if ~exist('dd1','var') || isempty(dd1), dd1 = 0.9; end %percentage of coherences to be shrinked
daniele@160 15 if ~exist('nIter','var') || isempty(nIter), nIter = 5; end %number of iterations
daniele@160 16
daniele@160 17 %% Compute svd and gramian
daniele@160 18 A = normc(initA); %normalise columns
daniele@160 19 [Uinit Sigma] = svd(A); %calculate svd of the matrix
daniele@160 20 G = A'*A; %gramian matrix
daniele@160 21
daniele@160 22 muMin = sqrt((m-n)/(n*(m-1))); %Lower bound on mutual coherence
daniele@160 23 res = zeros(nIter,1);
daniele@160 24 for iIter = 1:nIter
daniele@160 25 gg = sort(abs(G(:))); %sort inner products from less to ost correlated
daniele@160 26 pos = find(abs(G(:))>gg(round(dd1*(m^2-m))) & abs(G(:)-1)>1e-6);
daniele@160 27 G(pos) = G(pos)*dd2;
daniele@160 28 [U S V] = svd(G);
daniele@160 29 S(n+1:end,1+n:end) = 0;
daniele@160 30 G = U*S*V';
daniele@160 31 G = diag(1./abs(sqrt(diag(G))))*G*diag(1./abs(sqrt(diag(G))));
daniele@160 32 gg = sort(abs(G(:)));
daniele@160 33 pos = find(abs(G(:))>gg(round(dd1*(m^2-m))) & abs(G(:)-1)>1e-6);
daniele@160 34 res(iIter) = max(abs(G(pos)));
daniele@160 35 if verb
daniele@160 36 fprintf(1,'%6i %12.8f %12.8f %12.8f \n',...
daniele@160 37 [iIter,muMin,mean(abs(G(pos))),max(abs(G(pos)))]);
daniele@160 38 end
daniele@160 39 end
daniele@160 40
daniele@160 41 [~, Sigma_gram V_gram] = svd(G); %calculate svd decomposition of gramian
daniele@160 42 Sigma_new = sqrt(Sigma_gram(1:n,:)).*sign(Sigma);
daniele@160 43 A = Uinit*Sigma_new*V_gram';
daniele@160 44 A = normc(A);