rbmatlab  1.16.09
 All Classes Namespaces Files Functions Variables Modules Pages
orthonormalize_chol.m
1 function onvec = orthonormalize_chol(vec,A,epsilon)
2 % function onvec = orthonormalize_chol(vec[,A,epsilon])
3 %
4 % orthonormalization of vectors in columns of
5 % matrix vec to onvec by cholesky decomposition of gram matrix.
6 % the inner product matrix A can be specified additionally, i.e.
7 % <x,x> = x' * A * x;
8 %
9 % Makes use of
10 % G = vec' * A * vec = R' R
11 %
12 % by incomplete Cholesky Factorization
13 % and determines onvec by
14 % onvec * R = vec
15 %
16 % If diagonal vector of L is too small for some entry, this
17 % indicates a linear dependent vector. These are discarded
18 
19 % Bernard Haasdonk 22.8.2008
20 
21 if nargin < 3
22  epsilon = 1e-7; % => for nonlinear evolution this value is required.
23 end;
24 %epsilon = 1e-10;% => for linear evolution this value was OK.
25 %epsilon = 1e-12; %-> This causes error by returning non-orthogonal
26 % vectors (e.g. two identical vectors)
27 % So take epsilon larger than 1e-12!
28 
29 if isempty(vec)
30  onvec = zeros(size(vec));
31  return;
32 end;
33 
34 if nargin<2
35  A = 1;
36 end;
37 
38 % check on identity of vectors (can happen, that numerics does not detect
39 % this afterwards due to rounding errors!!)
40 
41 for i=1:(size(vec,2)-1)
42  for j=(i+1):size(vec,2)
43  if isequal(vec(:,i),vec(:,j))
44  vec(:,j) = 0;
45  end;
46  end;
47 end;
48 
49 onvec = vec;
50 
51 %for i = 1:size(vec,2);
52 % % orthogonalize next vector i and assume, that it is already
53 % % orthogonal to previous ones
54 % n = sqrt(onvec(:,i)' * A * onvec(:,i));
55 % if (n<epsilon)
56 % onvec(:,i) = 0;
57 % else
58 % onvec(:,i) = onvec(:,i)/n;
59 % end;
60 %
61 % % orthogonalize remaining vectors wrt this one:
62 %
63 % A_mult_onvec_i = A*onvec(:,i);
64 %
65 % % create row-vector with projections on the created on-vector
66 % coeffs= A_mult_onvec_i' * onvec(:,i+1:end);
67 %
68 % % create matrix of scaled versions of actual orthonormalized vector
69 % coeffmat = onvec(:,i) * coeffs;
70 %
71 % % perform orthogonalization
72 % onvec(:,i+1:end) = onvec(:,i+1:end) - coeffmat;
73 %
74 %end;
75 
76 % get gram matrix
77 G = onvec' * A * onvec;
78 G = 0.5* (G + G');
79 
80 options.droptol = epsilon;
81 options.rdiag = 1;
82 
83 %R = full(cholinc(sparse(G),'inf')); % fill small diagonal entries with inf
84 %R = full(cholinc(sparse(G),options)); % fill small diagonal entries with inf
85 R = full(cholinc(sparse(G),epsilon)); % cholesky with dropvalue epsilon
86 
87 %plot(diag(R));
88 %keyboard;
89 
90 ind = find(diag(R)>epsilon);
91 onvec = onvec(:,ind);
92 Ri = R(ind,ind);
93 
94 %L = chol(G,'lower');
95 
96 onvec = onvec / Ri;
97 
98 %Gi = G(i,i);
99 
100 % eliminate too small or too large vectors:
101 norms = onvec' * A * onvec;
102 ind = find(abs(diag(norms)-1)<0.5);
103 onvec = onvec(:,ind);
104 
105 %disp('check orthonormality!!');
106 %keyboard;
107 
108 % eliminate zero-columns
109 %nsqr = sum(onvec.^2);
110 %i = find(nsqr > 0.1);
111 %onvec = onvec(:,i);
112 
113 %resort zero-columns to back
114 %nsqr = sum(onvec.^2);
115 %[s,i] = sort(-nsqr);
116 %onvec = onvec(:,i);
117 
118 % TO BE ADJUSTED TO NEW SYNTAX
119 %| \docupdate