find index and value of max value of larger array based on range provided by another array

2 views (last 30 days)
I have an array "wave_height" 124x25792 (had to shorten due to file size). I have another array "defect_locations" 617x6. I would like to step through each row in "defect_locations" and find the max value and index from "wave_height" based on columns 4&5 in "defect_locations"; basically check all across the rows (width) given starting and stopping column values (length). the values would then be stored in columns 1,2,3 of "defect_locations".
How could I go about doing this? I think it should be pretty trivial I just can't seem to grasp it.
arrays are included in the attached .mat file.
Here is what I have so far:
for x = 1:length(defect_locations);
check_start = defect_locations(x,4);
check_stop = defect_locations(x,5);
defect_locations(x,3) = max(max(wave_height(:,check_start:check_stop)));
defect_locations(x,1) = %the row index of wave_height where the max value was found
defect_locations(x,2) = %the column index of wave_height where the max value was found
end

Accepted Answer

Jos (10584)
Jos (10584) on 2 Nov 2017
Something like this could work:
for x = 1:length(defect_locations)
check_start = defect_locations(x,4);
check_stop = defect_locations(x,5);
TMP = wave_height(:,check_start:check_stop) ; % extract the sub-matrix
[defect_locations(x,3), IDX] = max(TMP(:)) ; % find the overall value and linear index
[RI, CI] ind2sub(size(tmp), IDX) ; % convert to row and column subindices
defect_locations(x,1) = RI % the row index of wave_height where the max value was found
defect_locations(x,2) = CI + check_start - 1 %the column index of wave_height where the max value was found
end

More Answers (1)

KL
KL on 2 Nov 2017
Usually, when you use max, you can also extract the linear index of the maximum value, for example,
[M,I] = max(your_array)
but for you case you are only considering certain elements of a specific row, so you could use find. You get the row number directly since you find max across all rows but for column, you'll have to reindex it like the following,
defect_locations(x,3) = max(max(wave_height(:,check_start:check_stop)));
[defect_locations(x,1),ci] = find(wave_height(:,check_start:check_stop)==defect_locations(x,3));
defect_locations(x,2) = ci+check_start-1;
There are few other things about your code that I've noticed. Please be careful when you're using length. I'd actually recommend using size, if you want to get the number of rows use size(matrix,1) and for getting the column use, size(matrix,2). So you for loop should look like,
for k=1:size(defect_locations,1)
...
end
I haven't tested this code but it should work I hope.
  1 Comment
Munsell Randall
Munsell Randall on 2 Nov 2017
i appreciate the answer, it does produce the correct results. however, Jos's answer above runs in half the time.
Also, i appreciate the caution for "length". i will go through the rest of my code and remove the references for my MANY for loops.
I'm putting both answers in my code but commenting out one. I like having different ways of achieving the same result.

Sign in to comment.

Tags

Community Treasure Hunt

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

Start Hunting!