Advanced logical matrix indexing

11 visualizaciones (últimos 30 días)
Krzysztof
Krzysztof el 11 de Oct. de 2012
Is it possible to use one line of code to achieve the following
given an NxN matrix A construct an N-1xN matrix B where each column _n in B eliminates the _nth element from the _n column in A
e.g.
A = [1 1 1;2 2 2;3 3 3] gives B = [2 1 1;3 3 2]
I can do this in a for-loop, but given MATLAB is really bad at handling these I was hoping there is a faster solution
Thanks,
~K

Respuesta aceptada

James Tursa
James Tursa el 11 de Oct. de 2012
Another variation of Matt J's approach:
B = A(:);
B(1:(N+1):(N*N)) = [];
B = reshape(B,N-1,N);
  2 comentarios
Matt J
Matt J el 11 de Oct. de 2012
Interestingly, there's no need for B=A(:). It works just as well with B=A.
James Tursa
James Tursa el 11 de Oct. de 2012
I noticed that too, but the result is a 1D vector so you still need the reshape at the end.

Iniciar sesión para comentar.

Más respuestas (2)

Matt Fig
Matt Fig el 11 de Oct. de 2012
Editada: Matt Fig el 11 de Oct. de 2012
Given this array:
A = [1 1 1;2 2 2;3 3 3] % Must be n-by-n
% Remove the ith element of each ith column.
B = reshape(A(~eye(size(A))),size(A,1)-1,size(A,1))
.
.
.
EDIT
One could write a nifty little function to do this:
function A = removediag(A)
% Removes the diagonal elements of a square matrix.
% Author: Matt Fig
S = size(A);
if S(1)~=S(2)
error('REMOVEDIAG is only for square arrays');
end
A = reshape(A(~diag(true(1,S(1)))),S(1)-1,S(1));
  5 comentarios
Matt Fig
Matt Fig el 11 de Oct. de 2012
I see. It is still sparse, but the space saving is ruined. True enough.
Matt Fig
Matt Fig el 11 de Oct. de 2012
Editada: Matt Fig el 11 de Oct. de 2012
One could avoid the intermediate double (eye(size(A))) by using:
B = reshape(A(~diag(true(1,size(A,1)))),size(A,1)-1,size(A,1))
In fact this is 40% faster than my original solution for very large arrays.

Iniciar sesión para comentar.


Matt J
Matt J el 11 de Oct. de 2012
Editada: Matt J el 11 de Oct. de 2012
I don't think there's a 1-line solution (without creating your own mfile function), but you don't need loops:
B=A;
B(logical(speye(N)))=[];
B=reshape(B,N-1,N);

Categorías

Más información sobre Matrix Indexing en Help Center y File Exchange.

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by