Find max and min of groups in columns of a matrix

2 views (last 30 days)
I have a matrix with positive and negative values as:
a=[0 1;-3 3;-2 -7;0 5;4 -6;1 -2].
I would like to find by columns the maximum positive and minimum negative of each group of positive and negative values without any sorting. For the example given the result b would be:
b{1,1}= [-3;4]
b{1,2}= [3;-7;5;-6]
Thanks
  2 Comments
Walter Roberson
Walter Roberson on 31 Mar 2014
How is a "group" to be determined ? Are the group boundaries always marked by 0 in the first column? If so is the value in the second column of that row to be included or excluded from the calculations? Would you not also be wanting to record the boundaries of the groups found?
Dana
Dana on 1 Apr 2014
Each column must be analyzed independently, they are not connected. The boundary between groups is the change of sign. In the example, the first column would have two groups: [0;-3;-2] and [0;4;1]. The aim is find the minimum of the negative values and the maximum of the positive ones. The first group is a negative one and the minimum of them is -3. The second group is positive and the maximum is 4. The answer for first column is therefore [-3;4]. For the second column there are four groups:[1;3] [-7] [5] and [-6;-2]. The answer for the second column would be then [3;-7;5;-6]. And yes, I would like to record the boundaries of the groups also... Thanks

Sign in to comment.

Accepted Answer

Andrei Bobrov
Andrei Bobrov on 1 Apr 2014
Edited: Andrei Bobrov on 1 Apr 2014
a=[0 1;-3 3;-2 -7;0 5;4 -6;1 -2]
t = [true(1,size(a,2));diff(a<0)~=0];
ir = cumsum(t);
jj = max(ir);
ii = bsxfun(@plus,ir,[0,jj(1:end-1)]);
out1 = mat2cell(accumarray(ii(:),a(:),[],@(x)max(abs(x))*sign(sum(x))),jj,1);
out = cellfun(@(x)x(x~=0),out1,'un',0);
  1 Comment
Dana
Dana on 1 Apr 2014
Great! The only problem comes when there are Nans in the source data but it works for the rest of cases! I've got another solution but it's really inefficient...problems of being new with matlab! Thanks a lot!

Sign in to comment.

More Answers (1)

Joseph Cheng
Joseph Cheng on 31 Mar 2014
Why not break it up into the groups and handle them in a for loop? you can search for groups with groupstart = find(a(:,1)==0)
groupstart = find(a(:,1)==0)
after that you can use a for loop that does the min and max for a(groupstart(i):groupstart(i+1)-1,:)
  1 Comment
Dana
Dana on 1 Apr 2014
Thanks for that but the problem with this comes when there is a change of sign with no zero to be found by the find command.

Sign in to comment.

Categories

Find more on Loops and Conditional Statements 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!