0001 function M = euclideancomplexfactory(m, n)
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030 if ~exist('n', 'var') || isempty(n)
0031 if numel(m) == 1
0032 n = 1;
0033 else
0034 n = [];
0035 end
0036 end
0037
0038 dimensions_vec = [m(:)', n(:)'];
0039
0040 M.size = @() dimensions_vec;
0041
0042 M.name = @() sprintf('Euclidean space C^(%s)', num2str(dimensions_vec));
0043
0044 M.dim = @() 2*prod(dimensions_vec);
0045
0046 M.inner = @(x, d1, d2) real(d1(:)'*d2(:));
0047
0048 M.norm = @(x, d) norm(d(:), 'fro');
0049
0050 M.dist = @(x, y) norm(x(:)-y(:), 'fro');
0051
0052 M.typicaldist = @() sqrt(prod(dimensions_vec));
0053
0054 M.proj = @(x, d) d;
0055
0056 M.egrad2rgrad = @(x, g) g;
0057
0058 M.ehess2rhess = @(x, eg, eh, d) eh;
0059
0060 M.tangent = M.proj;
0061
0062 M.exp = @exp;
0063 function y = exp(x, d, t)
0064 if nargin == 3
0065 y = x + t*d;
0066 else
0067 y = x + d;
0068 end
0069 end
0070
0071 M.retr = M.exp;
0072
0073 M.log = @(x, y) y-x;
0074
0075 M.hash = @(x) ['z' hashmd5([real(x(:)) ; imag(x(:))])];
0076
0077 M.rand = @() (randn(dimensions_vec) + 1i*randn(dimensions_vec))/sqrt(2);
0078
0079 M.randvec = @randvec;
0080 function u = randvec(x)
0081 u = randn(dimensions_vec) + 1i*randn(dimensions_vec);
0082 u = u / norm(u(:), 'fro');
0083 end
0084
0085 M.lincomb = @matrixlincomb;
0086
0087 M.zerovec = @(x) zeros(dimensions_vec);
0088
0089 M.transp = @(x1, x2, d) d;
0090
0091 M.pairmean = @(x1, x2) .5*(x1+x2);
0092
0093 sz = prod(dimensions_vec);
0094 M.vec = @(x, u_mat) [real(u_mat(:)) ; imag(u_mat(:))];
0095 M.mat = @(x, u_vec) reshape(u_vec(1:sz), dimensions_vec) ...
0096 + 1i*reshape(u_vec((sz+1):end), dimensions_vec);
0097 M.vecmatareisometries = @() true;
0098 M.lie_identity = @() zeros(dimensions_vec);
0099
0100 end