Advanced logical matrix indexing
Show older comments
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
Accepted Answer
More Answers (2)
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 Comments
Matt J
on 11 Oct 2012
OK, so I guess there is a 1-line solution! I would slightly prefer mine, though, because it uses sparse indexing.
Matt Fig
on 11 Oct 2012
I see. It is still sparse, but the space saving is ruined. True enough.
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.
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);
Categories
Find more on Matrix Indexing in Help Center and File Exchange
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!