1 view (last 30 days)

Show older comments

In a previous post, I have created a matrix

1 1

1 2

1 3

1 4

1 5

2 1

2 2

2 3

2 4

2 5

For each 2D grid point I calculate some number in the third column

1 1 10

1 2 39

1 3 24

1 4 7

1 5 41

2 1 69

2 2 73

2 3 121

2 4 10

2 5 7

Then what I would like to do is to (1) choose the max of numbers in column 3 whose column 1 number is 1, 2, 3, 4,... and (2) also record the number of the second column for a row that the column 3 number is max. That is, I would like to create a matrix

1 5 41

2 3 121

3 ..

4 ..

5 ..

Please advise.

Mario Malic
on 24 Jul 2020

Edited: Mario Malic
on 24 Jul 2020

clearvars;

clc;

A = [1 1 10

1 2 39

1 3 24

1 4 7

1 5 41

2 1 69

2 2 73

2 3 121

2 4 10

2 5 7

3 1 9

3 2 15

3 3 100

3 4 131

3 5 133];

A_New = zeros(max(A(:,1)), 3);

for ii = 1 : 1 : max(A(:,1))

[Val,Ind] = max(A(5*(ii-1)+1:5*ii,3));

A_New (ii,1) = ii;

A_New (ii,2) = A(Ind,2);

A_New (ii,3) = Val;

end

John D'Errico
on 24 Jul 2020

This is the perfect problem for the accumarray function. I'll add a few rows.

A = [1 1 10

1 2 39

1 3 24

1 4 7

1 5 41

2 1 69

2 2 73

2 3 121

2 4 10

2 5 7

3 1 15

3 2 147

3 3 12

4 1 5];

Now, if you read the help for accumarray...

accumarray(A(:,1),A(:,3),[max(A(:,1)),1],@max)

ans =

41

121

147

5

The first column is an index. we will be accumulating things on this index. For each value of that column, we will look at the replicates in the first column, and then work with the comparable numbers for the second argument of accumarray.

The third argument to accumarray tells it the final size of the array. ANd the 4th argument tells it to compute the max for each index.

Essentially, in one line of code, you get exactly what you wanted to see done.

Jim Riggs
on 24 Jul 2020

Edited: Jim Riggs
on 24 Jul 2020

Look into using logical indexing.

Not my strong point, but for example, if A is the 3 x 10 matrix, you can select all cases where the first column is 1 using

B = A(A(:,1,1)==1,:,:)

This results in matrix B:

1 1 10

1 2 39

1 3 24

1 4 7

1 5 41

Likewise, using

C = A(A(:,1,1)==2,:,:)

gives the following matrix C:

2 1 69

2 2 73

2 3 121

2 4 10

2 5 7

Bruno Luong
on 24 Jul 2020

assuming your grid is 1:5 x 1:5, so A is (25 x 3). Example of fake data

i=1:5

i =

1 2 3 4 5

j=1:5

j =

1 2 3 4 5

[I,J]=meshgrid(i,j);

Z=ceil(20*rand(size(I)));

A=[I(:) J(:) Z(:)]

A =

1 1 13

1 2 17

1 3 18

1 4 4

1 5 2

2 1 7

2 2 13

2 3 8

2 4 19

2 5 2

3 1 20

3 2 14

3 3 13

3 4 3

3 5 1

4 1 12

4 2 1

4 3 15

4 4 5

4 5 6

5 1 20

5 2 4

5 3 16

5 4 1

5 5 7

Now here is the code

Z = reshape(A(:,3),[5 5]);

[zmax,jmax] = max(Z,[],1);

i = 1:5; % ==A(1:5:end,1);

[i(:) jmax(:) zmax(:)]

returns

ans =

1 3 18

2 4 19

3 1 20

4 3 15

5 1 20

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

Start Hunting!