Home > manopt > tools > powermanifold.m

powermanifold

PURPOSE ^

Returns a structure describing a power manifold M^n = M x M x ... x M.

SYNOPSIS ^

function Mn = powermanifold(M, n)

DESCRIPTION ^

 Returns a structure describing a power manifold M^n = M x M x ... x M.

 function Mn = powermanifold(M, n)

 Input: a manifold structure M and an integer n >= 1.
 
 Output: a manifold structure Mn representing M x ... x M (n copies of M)
 with the metric of M extended element-wise. Points and vectors are stored
 as cells of size nx1.

 This code is for prototyping uses. The structures returned are often
 inefficient representations of power manifolds owing to their use of
 for-loops, but they should allow to rapidly try out an idea.

 Example (an inefficient representation of the oblique manifold (3, 10)):
 Mn = powermanifold(spherefactory(3), 10)
 disp(Mn.name());
 x = Mn.rand()

 See also: productmanifold

CROSS-REFERENCE INFORMATION ^

This function calls: This function is called by:

SUBFUNCTIONS ^

SOURCE CODE ^

0001 function Mn = powermanifold(M, n)
0002 % Returns a structure describing a power manifold M^n = M x M x ... x M.
0003 %
0004 % function Mn = powermanifold(M, n)
0005 %
0006 % Input: a manifold structure M and an integer n >= 1.
0007 %
0008 % Output: a manifold structure Mn representing M x ... x M (n copies of M)
0009 % with the metric of M extended element-wise. Points and vectors are stored
0010 % as cells of size nx1.
0011 %
0012 % This code is for prototyping uses. The structures returned are often
0013 % inefficient representations of power manifolds owing to their use of
0014 % for-loops, but they should allow to rapidly try out an idea.
0015 %
0016 % Example (an inefficient representation of the oblique manifold (3, 10)):
0017 % Mn = powermanifold(spherefactory(3), 10)
0018 % disp(Mn.name());
0019 % x = Mn.rand()
0020 %
0021 % See also: productmanifold
0022 
0023 % This file is part of Manopt: www.manopt.org.
0024 % Original author: Nicolas Boumal, Dec. 30, 2012.
0025 % Contributors:
0026 % Change log:
0027 %   NB, July 4, 2013: Added support for vec, mat, tangent.
0028 %                     Added support for egrad2rgrad and ehess2rhess.
0029 
0030     
0031     assert(n >= 1, 'n must be an integer larger than or equal to 1.');
0032     
0033     Mn.name = @() sprintf('[%s]^%d', M.name(), n);
0034     
0035     Mn.dim = @() n*M.dim();
0036     
0037     Mn.inner = @inner;
0038     function val = inner(x, u, v)
0039         val = 0;
0040         for i = 1 : n
0041             val = val + M.inner(x{i}, u{i}, v{i});
0042         end
0043     end
0044 
0045     Mn.norm = @(x, d) sqrt(Mn.inner(x, d, d));
0046 
0047     Mn.dist = @dist;
0048     function d = dist(x, y)
0049         sqd = 0;
0050         for i = 1 : n
0051             sqd = sqd + M.dist(x{i}, y{i})^2;
0052         end
0053         d = sqrt(sqd);
0054     end
0055 
0056     Mn.typicaldist = @typicaldist;
0057     function d = typicaldist()
0058         sqd = 0;
0059         for i = 1 : n
0060             sqd = sqd + M.typicaldist()^2;
0061         end
0062         d = sqrt(sqd);
0063     end
0064     
0065     Mn.proj = @proj;
0066     function u = proj(x, u)
0067         for i = 1 : n
0068             u{i} = M.proj(x{i}, u{i});
0069         end
0070     end
0071     
0072     Mn.tangent = @tangent;
0073     function u = tangent(x, u)
0074         for i = 1 : n
0075             u{i} = M.tangent(x{i}, u{i});
0076         end
0077     end
0078     
0079     if isfield(M, 'tangent2ambient_is_identity')
0080         Mn.tangent2ambient_is_identity = M.tangent2ambient_is_identity;
0081     else
0082         Mn.tangent2ambient_is_identity = true;
0083     end
0084     
0085     if isfield(M, 'tangent2ambient')
0086         Mn.tangent2ambient = @tangent2ambient;
0087     else
0088         Mn.tangent2ambient = @(x, u) u;
0089     end
0090     function u = tangent2ambient(x, u)
0091         for i = 1 : n
0092             u{i} = M.tangent2ambient(x{i}, u{i});
0093         end
0094     end
0095     
0096     Mn.egrad2rgrad = @egrad2rgrad;
0097     function g = egrad2rgrad(x, g)
0098         for i = 1 : n
0099             g{i} = M.egrad2rgrad(x{i}, g{i});
0100         end
0101     end
0102     
0103     Mn.ehess2rhess = @ehess2rhess;
0104     function h = ehess2rhess(x, eg, eh, h)
0105         for i = 1 : n
0106             h{i} = M.ehess2rhess(x{i}, eg{i}, eh{i}, h{i});
0107         end
0108     end
0109     
0110     Mn.exp = @expo;
0111     function x = expo(x, u, t)
0112         if nargin < 3
0113             t = 1.0;
0114         end
0115         for i = 1 : n
0116             x{i} = M.exp(x{i}, u{i}, t);
0117         end
0118     end
0119     
0120     Mn.retr = @retr;
0121     function x = retr(x, u, t)
0122         if nargin < 3
0123             t = 1.0;
0124         end
0125         for i = 1 : n
0126             x{i} = M.retr(x{i}, u{i}, t);
0127         end
0128     end
0129     
0130     if isfield(M, 'log')
0131         Mn.log = @loga;
0132     end
0133     function u = loga(x, y)
0134         u = cell(n, 1);
0135         for i = 1 : n
0136             u{i} = M.log(x{i}, y{i});
0137         end
0138     end
0139     
0140     Mn.hash = @hash;
0141     function str = hash(x)
0142         str = '';
0143         for i = 1 : n
0144             str = [str M.hash(x{i})]; %#ok<AGROW>
0145         end
0146         str = ['z' hashmd5(str)];
0147     end
0148 
0149     Mn.lincomb = @lincomb;
0150     function x = lincomb(x, a1, u1, a2, u2)
0151         if nargin == 3
0152             for i = 1 : n
0153                 x{i} = M.lincomb(x{i}, a1, u1{i});
0154             end
0155         elseif nargin == 5
0156             for i = 1 : n
0157                 x{i} = M.lincomb(x{i}, a1, u1{i}, a2, u2{i});
0158             end
0159         else
0160             error('Bad usage of powermanifold.lincomb');
0161         end
0162     end
0163 
0164     Mn.rand = @rand;
0165     function x = rand()
0166         x = cell(n, 1);
0167         for i = 1 : n
0168             x{i} = M.rand();
0169         end
0170     end
0171 
0172     Mn.randvec = @randvec;
0173     function u = randvec(x)
0174         u = cell(n, 1);
0175         for i = 1 : n
0176             u{i} = M.randvec(x{i});
0177         end
0178         u = Mn.lincomb(x, 1/sqrt(n), u);
0179     end
0180 
0181     Mn.zerovec = @zerovec;
0182     function u = zerovec(x)
0183         u = cell(n, 1);
0184         for i = 1 : n
0185             u{i} = M.zerovec(x{i});
0186         end
0187     end
0188 
0189     if isfield(M, 'transp')
0190         Mn.transp = @transp;
0191     end
0192     function u = transp(x1, x2, u)
0193         for i = 1 : n
0194             u{i} = M.transp(x1{i}, x2{i}, u{i});
0195         end
0196     end
0197 
0198     if isfield(M, 'pairmean')
0199         Mn.pairmean = @pairmean;
0200     end
0201     function y = pairmean(x1, x2)
0202         y = cell(n, 1);
0203         for i = 1 : n
0204             y{i} = M.pairmean(x1{i}, x2{i});
0205         end
0206     end
0207 
0208     % Compute the length of a vectorized tangent vector of M at x, assuming
0209     % this length is independent of the point x (that should be fine).
0210     if isfield(M, 'vec')
0211         rand_x = M.rand();
0212         zero_u = M.zerovec(rand_x);
0213         len_vec = length(M.vec(rand_x, zero_u));
0214 
0215         Mn.vec = @vec;
0216         
0217         if isfield(M, 'mat')
0218             Mn.mat = @mat;
0219         end
0220         
0221     end
0222     
0223     function u_vec = vec(x, u_mat)
0224         u_vec = zeros(len_vec, n);
0225         for i = 1 : n
0226             u_vec(:, i) = M.vec(x{i}, u_mat{i});
0227         end
0228         u_vec = u_vec(:);
0229     end
0230 
0231     function u_mat = mat(x, u_vec)
0232         u_mat = cell(n, 1);
0233         u_vec = reshape(u_vec, len_vec, n);
0234         for i = 1 : n
0235             u_mat{i} = M.mat(x{i}, u_vec(:, i));
0236         end
0237     end
0238 
0239     if isfield(M, 'vecmatareisometries')
0240         Mn.vecmatareisometries = M.vecmatareisometries;
0241     else
0242         Mn.vecmatareisometries = @() false;
0243     end
0244 
0245 end

Generated on Mon 10-Sep-2018 11:48:06 by m2html © 2005