Discover MakerZone

MATLAB and Simulink resources for Arduino, LEGO, and Raspberry Pi

Learn more

Discover what MATLAB® can do for your career.

Opportunities for recent engineering grads.

Apply Today

Thread Subject:
Diagonal of a matrix vector

Subject: Diagonal of a matrix vector

From: Mauro

Date: 5 Oct, 2010 19:23:31

Message: 1 of 9

I have a "matrix" with dimensions (n,n,M), which can be interpreted as
a vector of M n-by-n matrices. Is there a away for me to take the
diagonal of all these M matrices at once? I.e. taking the diagonal
only with respect to the first two dimensions.

Subject: Diagonal of a matrix vector

From: Sean

Date: 5 Oct, 2010 19:35:27

Message: 2 of 9

Mauro <msmscarlatti@googlemail.com> wrote in message <f13aac49-c83e-432e-8697-60e7a8963834@x42g2000yqx.googlegroups.com>...
> I have a "matrix" with dimensions (n,n,M), which can be interpreted as
> a vector of M n-by-n matrices. Is there a away for me to take the
> diagonal of all these M matrices at once? I.e. taking the diagonal
> only with respect to the first two dimensions.

Like this:

M = repmat(magic(4),[1 1 4]);
M(logical(repmat(eye(4),[1 1 4])))

Subject: Diagonal of a matrix vector

From: Matt J

Date: 5 Oct, 2010 20:11:21

Message: 3 of 9

Another solution

%%Fake data
n=4;M=3;
A=rand(n,n,M),


%Put the diagonals of each slice in columns of "Diags";

idx=bsxfun(@plus,(1:n+1:n^2).',(0:M-1)*n^2);

Diags= reshape( A(idx) , n,[]) , %the result

Subject: Diagonal of a matrix vector

From: Mauro

Date: 5 Oct, 2010 20:20:15

Message: 4 of 9

Thanks to both of you, but I did not explain very clearly: what I
actually need is to replace each matrix in the "vector" with its
diagonal version.

Subject: Diagonal of a matrix vector

From: Matt J

Date: 5 Oct, 2010 20:30:41

Message: 5 of 9

Mauro <msmscarlatti@googlemail.com> wrote in message <06c553f7-b981-49c1-b937-5763c8f12af1@x42g2000yqx.googlegroups.com>...
> Thanks to both of you, but I did not explain very clearly: what I
> actually need is to replace each matrix in the "vector" with its
> diagonal version.
======


theResult=bsxfun(@times,A,eye(n)),

Subject: Diagonal of a matrix vector

From: Sean

Date: 5 Oct, 2010 20:40:09

Message: 6 of 9

"Matt J " <mattjacREMOVE@THISieee.spam> wrote in message <i8g1th$kuf$1@fred.mathworks.com>...
> Mauro <msmscarlatti@googlemail.com> wrote in message <06c553f7-b981-49c1-b937-5763c8f12af1@x42g2000yqx.googlegroups.com>...
> > Thanks to both of you, but I did not explain very clearly: what I
> > actually need is to replace each matrix in the "vector" with its
> > diagonal version.
> ======
>
>
> theResult=bsxfun(@times,A,eye(n)),

Or:
n = 400;
m = 300;

A = repmat(magic(n),[1 1 m]);
theResult2 = A.*repmat(eye(n),[1 1 m]);

Though the bsxfun solution is much faster:

tic
theResult2 = A.*repmat(eye(n),[1 1 m]);
toc
tic
theResult1=bsxfun(@times,A,eye(n));
toc
isequal(theResult1,theResult2)
%{
Elapsed time is 8.480145 seconds.
Elapsed time is 0.877621 seconds.

ans =

     1
%}

Subject: Diagonal of a matrix vector

From: James Tursa

Date: 5 Oct, 2010 21:26:19

Message: 7 of 9

"Matt J " <mattjacREMOVE@THISieee.spam> wrote in message <i8g1th$kuf$1@fred.mathworks.com>...
> Mauro <msmscarlatti@googlemail.com> wrote in message <06c553f7-b981-49c1-b937-5763c8f12af1@x42g2000yqx.googlegroups.com>...
> > Thanks to both of you, but I did not explain very clearly: what I
> > actually need is to replace each matrix in the "vector" with its
> > diagonal version.
> ======
>
>
> theResult=bsxfun(@times,A,eye(n)),

Probably not an issue with OP, but the above does not clear any inf or NaN values from the off-diagonal positions in the array ... they persist even after multiplying by 0. An alternate method that does clear these values from the off-diagonal elements is:

X = repmat(logical(eye(n)),1,M);
A(~X) = 0;

James Tursa

Subject: Diagonal of a matrix vector

From: Matt J

Date: 5 Oct, 2010 21:38:21

Message: 8 of 9

"James Tursa" <aclassyguy_with_a_k_not_a_c@hotmail.com> wrote in message <i8g55r$qme$1@fred.mathworks.com>...

> Probably not an issue with OP, but the above does not clear any inf or NaN values from the off-diagonal positions in the array ... they persist even after multiplying by 0. An alternate method that does clear these values from the off-diagonal elements is:
>
> X = repmat(logical(eye(n)),1,M);
> A(~X) = 0;
>
=============

True, but because I'm so anti-REPMAT, I would opt for the following,

idx=bsxfun(@plus,(1:n+1:n^2).',(0:M-1)*n^2);
B=zeros(size(A));
B(idx)=A(idx);

Subject: Diagonal of a matrix vector

From: Mauro

Date: 6 Oct, 2010 10:56:23

Message: 9 of 9

Thank you very much for all your help, guys!

Tags for this Thread

What are tags?

A tag is like a keyword or category label associated with each thread. Tags make it easier for you to find threads of interest.

Anyone can tag a thread. Tags are public and visible to everyone.

Contact us