How to intersect a matrix with a set and keep the rows of the matrix?

3 views (last 30 days)
I'm trying to intersect an N by M matrix, 'A', with a set (a 1 by X matrix), 'B', but am trying to do so by rows. (e.g. A(1:M) intersect B ).
So I would end up with an N by '__' matrix where the rows are the intersection of the respective row and set 'B', rather than a large set.
Is there a way to do this without using a for loop?
  6 Comments
James Tursa
James Tursa on 25 Aug 2015
There are various ways to do it (padding, cell arrays, etc) ... we just need to know what you want for an output.
Rion Wilson-Yue
Rion Wilson-Yue on 25 Aug 2015
Edited: Rion Wilson-Yue on 25 Aug 2015
In the very end I'm looking for the min and max of the intersection of a row and the 1xX array. I want to keep the rows so I can get the min and max for each of them.
So long as I can get that and keep the script fast, format doesn't really matter. And if you can suggest a better way of doing this I'm open to that as well.

Sign in to comment.

Accepted Answer

Kelly Kearney
Kelly Kearney on 25 Aug 2015
If you only want to get the min and max of each row, and really want to avoid for loops, here's a solution. This gives the min and max for each row of A, ignoring values not in B, which is I think what you are looking for.
A = [...
2 12 6 4 8
1 3 5 7 9
];
B = [ 1 2 3 4 5 6 ];
tf = ismember(A, B);
Amax = A;
Amin = A;
Amax(~tf) = -Inf;
Amin(~tf) = Inf;
maxval = max(Amax, [], 2);
minval = min(Amin, [], 2);
results
>> maxval
maxval =
6
5
>> minval
minval =
2
1
  4 Comments
Rion Wilson-Yue
Rion Wilson-Yue on 25 Aug 2015
Interesting... If I don't care about preserving the data could I use NaN instead of +/- Inf and then just replace the elements in 'A'?
Kelly Kearney
Kelly Kearney on 26 Aug 2015
Edited: Kelly Kearney on 26 Aug 2015
Yes, that would work. I always forget that min/max ignore NaNs by default.

Sign in to comment.

More Answers (1)

Image Analyst
Image Analyst on 25 Aug 2015
How about a not-too-fancy but simple, intuitive, and easy to understand "for" loop?
A = randi(20, 2, 15) % Sample data
B = [ 1 2 3 4 5 6 ] % What we're looking for
C = NaN(size(A)); % Preallocate
% Check each row one at a time.
for row = 1 : size(A, 1)
% Find intersection.
B_in_A = intersect(A(row, :), B)
% Stuff them into C
C(row, 1:length(B_in_A)) = B_in_A;
end
% Display C
C
  4 Comments
Rion Wilson-Yue
Rion Wilson-Yue on 25 Aug 2015
Yes yes, I know how fast a for loop is. And yes odds are it would, in all probablity, be fine to use a for loop, and even then this smidgen of code would still not be the system's bottle neck. But I'm trying to move from C thinking to MATLAB thinking (using matrix math/functions), and would also like to see how fast I can make this run.
While the difference in time may be insignificant I'd still like to know if this can be done without a for loop. This is why I asked my question (see last line in original question).
Image Analyst
Image Analyst on 25 Aug 2015
Not that I can think of off the top of my head. The problem is that you want your answers row-by-row, and each row has a different number of numbers, so all I can think of is a row-by-row solution.

Sign in to comment.

Community Treasure Hunt

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

Start Hunting!