How to get indices of unique elements in matrix in separate arrays
5 views (last 30 days)
Show older comments
1.I have a 1D array eg. A=[2,5,7,8,3,9.....]. Elements have been extracted from a 2d matrix eg
M= [1 5 2 17
2 2 8 9
3 4 7 5
..............]
2. Now, I need to find the indices of each element of A in Matrix M. Like,
A[1]= [1,3; 2,1; 2,2]
A[2]= [1,2;3,4]
A[3]= [3,3]
A[4]= [3,4].... so and so...
What is the nest way to do?
0 Comments
Accepted Answer
Jan
on 7 Feb 2017
Edited: Jan
on 7 Feb 2017
I would prefer one of the above suggestions, but for completeness a dull (but unexpectedly faster) loop:
M = [1 5 2 17; ...
2 2 8 9; ...
3 4 7 5];
A = [2,5,7,8,3,9];
R = cell(1, max(A));
for iA = A
[r, c] = find(M == iA);
R{iA} = [r, c];
end
A small speed comparison:
M = randi([1, 100], 100, 100);
A = randperm(100, 80);
tic;
for kk = 1:100
[R,C] = arrayfun(@(n)find(M==n),A,'Uni',0);
Z = cellfun(@(r,c)[r(:),c(:)],R,C,'Uni',0);
end
toc;
tic;
for kk = 1:100
[tf, idx] = ismember(M, A);
used_subset = idx(tf);
linear_idx = (1:numel(idx)).';
indices = accumarray( used_subset, linear_idx(tf), [], @(C) {C}, {});
r = size(M,1);
locations = cellfun(@(LI) [mod(LI-1, r)+1, floor((LI-1)/r)+1], ...
indices, 'Uniform', 0);
end
toc;
tic;
for kk = 1:100
R = cell(1, max(A));
for iA = A
[r, c] = find(M == iA);
R{iA} = [r, c];
end
end
toc;
tic;
for kk = 1:100
locations = regionprops(M, 'PixelList');
locations = {locations(A)};
end
toc;
% Matlab R2016b/64, Win7, Core2Duo
Elapsed time is 0.700541 seconds. % arrayfun/cellfun
Elapsed time is 0.789638 seconds. % accumarray
Elapsed time is 0.455393 seconds. % dull loop/find
... Could someone please post the results with regionprops of the IPT?
Oh, the dull loop runs fastert than it looks like.
0 Comments
More Answers (3)
Stephen23
on 7 Feb 2017
>> [R,C] = arrayfun(@(n)find(M==n),A,'Uni',0);
>> Z = cellfun(@(r,c)[r(:),c(:)],R,C,'Uni',0);
>> Z{:}
ans =
2 1
2 2
1 3
ans =
1 2
3 4
ans =
3 3
ans =
2 3
ans =
3 1
ans =
2 4
0 Comments
Guillaume
on 7 Feb 2017
Edited: Guillaume
on 7 Feb 2017
Another option, if you have the image processing toolbox, and assuming all the values in A and M are strictly positive integers:
locations = regionprops(M, 'PixelList');
locations = {locations(A).PixelList}
Note that rows and columns are swapped because mathworks can't settle on just one coordinate system.
0 Comments
Walter Roberson
on 7 Feb 2017
[tf, idx] = ismember(M, A);
used_subset = idx(tf);
linear_idx = (1:numel(idx)).';
indices = accumarray( used_subset, linear_idx(tf), [], @(C) {C}, {});
r = size(M,1);
locations = cellfun(@(LI) [mod(LI-1, r)+1, floor((LI-1)/r)+1], indices, 'Uniform', 0);
Note: this might have difficulty if there were elements in A that were not originally in M.
0 Comments
See Also
Categories
Find more on Structures 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!