Home > tt2 > @tt_matrix > axpx.m

axpx

PURPOSE ^

Matrix-by-vector multiplication with projection onto the tangent space

SYNOPSIS ^

function [y]=axpx(a,x)

DESCRIPTION ^

Matrix-by-vector multiplication with projection onto the tangent space
   [y]=AXPX(A,X) Multiplies matrix A by a vector X and projects the
   result onto the tangent space of the TT-manifold at point X. This
   function can be used in the construction of efficient dynamical
   low-rank TT-approximations

 TT-Toolbox 2.2, 2009-2012

This is TT Toolbox, written by Ivan Oseledets et al.
Institute of Numerical Mathematics, Moscow, Russia
webpage: http://spring.inm.ras.ru/osel

For all questions, bugs and suggestions please mail
ivan.oseledets@gmail.com
---------------------------

CROSS-REFERENCE INFORMATION ^

This function calls: This function is called by:

SOURCE CODE ^

0001 function [y]=axpx(a,x)
0002 %Matrix-by-vector multiplication with projection onto the tangent space
0003 %   [y]=AXPX(A,X) Multiplies matrix A by a vector X and projects the
0004 %   result onto the tangent space of the TT-manifold at point X. This
0005 %   function can be used in the construction of efficient dynamical
0006 %   low-rank TT-approximations
0007 %
0008 % TT-Toolbox 2.2, 2009-2012
0009 %
0010 %This is TT Toolbox, written by Ivan Oseledets et al.
0011 %Institute of Numerical Mathematics, Moscow, Russia
0012 %webpage: http://spring.inm.ras.ru/osel
0013 %
0014 %For all questions, bugs and suggestions please mail
0015 %ivan.oseledets@gmail.com
0016 %---------------------------
0017 d=x.d;
0018 n=a.n;
0019 m=a.m;
0020 rx=x.r;
0021 psx=x.ps;
0022 att=a.tt;
0023 corea=att.core;
0024 psa=att.ps;
0025 ra=att.r;
0026 %Do right-to-left orthogonalization and computation of psi
0027 %matrices
0028 corex=x.core;
0029 pos1=psx(d+1);
0030 psi=cell(d+1,1); %Psi-matrices
0031 psi{d+1}=1; psi{1}=1;
0032 cr1=corex(psx(d):psx(d+1)-1);
0033 y=x;
0034 corey=y.core;
0035 psy=y.ps;
0036 ry=y.r;
0037 for i=d:-1:2 
0038    %  fprintf('i=%d \n');
0039    cr2=corey(psy(i-1):psy(i)-1);
0040    cr1=reshape(cr1,[ry(i),n(i)*ry(i+1)]);
0041    cr2=reshape(cr2,[ry(i-1)*n(i-1),ry(i)]);
0042    cr1=cr1.';
0043    [q,rm]=qr(cr1,0); rn=size(q,2); rm=rm.';
0044    q=q.'; 
0045    ry(i)=rn;
0046    corey(pos1-ry(i+1)*n(i)*ry(i):pos1-1)=q(:);
0047       %Convolution is now performed for psi(i) using psi(i+1) and corea, and
0048    %(new) core q
0049    cra=corea(psa(i):psa(i+1)-1); cra=reshape(cra,[ra(i),n(i),m(i),ra(i+1)]);
0050    cry=reshape(conj(q),[ry(i),n(i),ry(i+1)]);
0051    crx=corex(psx(i):psx(i+1)-1);
0052    crx=reshape(crx,[rx(i),m(i),rx(i+1)]);
0053    pscur=psi{i+1}; pscur=reshape(pscur,[ra(i+1),rx(i+1),ry(i+1)]); %ra,rx,ry
0054    %First, convolve over rx(i+1)
0055    crx=reshape(crx,[rx(i)*m(i),rx(i+1)]);
0056     pscur=permute(pscur,[2,1,3]); pscur=reshape(pscur,[rx(i+1),ra(i+1)*ry(i+1)]);
0057    pscur=crx*pscur; %pscur is now rx(i)*m(i)*ra(i+1)*ry(i+1)
0058    %Convolve over m(i),ra(i+1),n(i),ry(i+1)
0059     pscur=reshape(pscur,[rx(i),m(i)*ra(i+1),ry(i+1)]);
0060     pscur=permute(pscur,[1,3,2]); 
0061     pscur=reshape(pscur,[rx(i)*ry(i+1),m(i)*ra(i+1)]);
0062     cra=reshape(cra,[ra(i)*n(i),m(i)*ra(i+1)]); cra=cra.';  
0063     pscur=pscur*cra; 
0064     %pscur is now rx(i)*ry(i+1)*ra(i)*n(i), it is left to convolve over
0065     %n(i)*ry(i+1)
0066     pscur=reshape(pscur,[rx(i),ry(i+1),ra(i),n(i)]);
0067     pscur=permute(pscur,[3,1,4,2]);
0068     pscur=reshape(pscur,[ra(i)*rx(i),n(i)*ry(i+1)]);
0069     cry=reshape(cry,[ry(i),n(i)*ry(i+1)]); cry=cry.';
0070     pscur=pscur*cry; %pscur is ra*rx*ry
0071     pscur=reshape(pscur,[rx(i),ra(i),ry(i)]);
0072     psi{i}=pscur;
0073    %End of psi-block
0074    pos1=pos1-ry(i+1)*n(i)*ry(i);
0075    cr1=cr2*rm;
0076 end
0077 corey(pos1-ry(2)*n(1)*ry(1):pos1-1)=cr1(:);
0078 pos1=pos1-ry(2)*n(1)*ry(1);
0079 corey=corey(pos1:end); %Truncate unused elements
0080 %Now compute the projection itself while recomputing psi-matrices
0081  pos1=1;
0082  psy=cumsum([1;n.*ry(1:d).*ry(2:d+1)]);
0083  rm=1;
0084  %keyboard;
0085   for i=1:d
0086           %Our convolution is
0087      %ps1(ra(i),rx(i),ry(i))*cra(ra(i),n(i),m(i),ra(i+1))
0088      %*ps2(ra(i+1),rx(i+1),ry(i+1))*crx(rx(i),m(i)*rx(i+1))->
0089      %cry(ry(i),n(i),ry(i+1)
0090 
0091      ps1=psi{i}; ps2=psi{i+1};
0092      cra=corea(psa(i):psa(i+1)-1);
0093      crx=corex(psx(i):psx(i+1)-1);
0094 %     corey(psy(i):psy(i+1)-1)=crx(:);
0095 %     y.core=corey;
0096 %          psy=cumsum([1;n.*ry(1:d).*ry(2:d+1)]);
0097 %     y.ps=psy;
0098      ps1=reshape(ps1,[ra(i),rx(i),ry(i)]);
0099      ps1=permute(ps1,[2,3,1]);
0100      ps1=reshape(ps1,[rx(i)*ry(i),ra(i)]);
0101      cra=reshape(cra,[ra(i),n(i)*m(i)*ra(i+1)]);
0102      cry=ps1*cra;      %cry is rx(i)*ry(i)*n(i)*m(i)*ra(i+1)
0103      %convolve over m(i),rx(i) with crx
0104      cry=reshape(cry,[rx(i),ry(i),n(i),m(i),ra(i+1)]);
0105      cry=permute(cry,[2,3,5,1,4]);
0106      cry=reshape(cry,[ry(i)*n(i)*ra(i+1),rx(i)*m(i)]);
0107      crx=reshape(crx,[rx(i)*m(i),rx(i+1)]);
0108      cry=cry*crx; cry0=cry;
0109      %cry is ry(i)*n(i)*ra(i+1)*rx(i+1)
0110      cry=reshape(cry,[ry(i)*n(i),ra(i+1)*rx(i+1)]);
0111      ps2=reshape(ps2,[ra(i+1)*rx(i+1),ry(i+1)]);
0112      %cry0=cry; %cry0 is ry(i)*n(i)*ra(i+1)*rx(i+1), convolution over ry(i)*n(i) will bring new psi --- not true; new psi will be brought with and
0113      %orthogonalization
0114      cry=cry*ps2;
0115       corey(pos1:pos1+ry(i)*n(i)*ry(i+1)-1)=cry(:);
0116       y.core=corey;
0117       psy=cumsum([1;n.*ry(1:d).*ry(2:d+1)]);
0118       y.ps=psy;
0119        %keyboard;
0120     
0121      cry=reshape(cry,[ry(i)*n(i),ry(i+1)]);
0122      [q,rm]=qr(cry,0);
0123      rn=size(q,2);
0124      ry(i+1)=rn;
0125      %q=q*rm;
0126      corey(pos1:pos1+ry(i)*n(i)*ry(i+1)-1)=q(:);
0127      pos1=pos1+ry(i)*n(i)*ry(i+1);
0128      %And now --- orthogonalization! (of cry) (he-he)
0129      %Now compute "new" psi
0130      %We need to compute
0131           %cry is rx(i)*ry(i)*n(i)*m(i)*ra(i+1)
0132      %convolve over m(i),rx(i) with crx
0133      %cry0 is ry(i)*n(i)*ra(i+1)*rx(i+1);
0134      cry0=reshape(cry0,[ry(i),n(i),ra(i+1),rx(i+1)]);
0135      cry0=permute(cry0,[3,4,1,2]);
0136      cry0=reshape(cry0,[ra(i+1)*rx(i+1),ry(i)*n(i)]);
0137      q=reshape(conj(q),[ry(i)*n(i),ry(i+1)]);
0138      psi{i+1}=cry0*q;
0139      
0140   end
0141   psy=cumsum([1;n.*ry(1:d).*ry(2:d+1)]);
0142   corey(psy(i):psy(i+1)-1)=corey(psy(i):psy(i+1)-1)*rm;
0143   y.core=corey;
0144   y.r=ry;
0145   y.ps=psy;
0146   y.n=n;
0147   y.d=d;
0148   return
0149 end

Generated on Wed 08-Feb-2012 18:20:24 by m2html © 2005