Clear Filters
Clear Filters

How to make a matrix based on other values in a matrix that 'match'

6 views (last 30 days)
Hi, I'm trying to create a matrix that is based on the values of another matrix and based on the number positioning of it's current matrix.
Here is where we start (MatrixONE):
The above matrix was done with the help of Stephen Cobeldick.
These are the values I require (MatrixTWO):
[ 1 100 120 ; 2 200 240 ; 3 300 360 ; 4 400 480 ]
For example, in the first row, first column. There is a value of 2. This value needs to collect the value from the second row, second column of MatrixTWO (Which is 200). Now in the first row of the second column is also a value of 2. However that value needs to collect the value 240. With negative numbers, they do the exact same thing but make the number negative. I've provided a picture of what the output should look like.
This is what the output should look like (MatrixTHREE):
One final note: This cannot be hard coded and must work 'universally'. This is where I get completely thrown off course.
I look forward to reading some answers!

Accepted Answer

Stephen23
Stephen23 on 23 Apr 2018
Edited: Stephen23 on 23 Apr 2018
Based on my earlier answer. Note in the code below the indices refer to this transposed matrices.
>> M1 = [1,2;2,3;3,4;1,3;1,4]
M1 =
1 2
2 3
3 4
1 3
1 4
>> M2 = [1,100,120;2,200,240;3,300,360;4,400,480]
M2 =
1 100 120
2 200 240
3 300 360
4 400 480
>> tmp = M1.'; % because MATLAB operates down columns
>> idx = tmp~=1; % input logical indices
>> [~,idc] = find(idx); % output column indices
>> idr = tmp(idx)-1; % output row indices
>> mat = zeros(max([idr,idc])); % preallocate the intermediate matrix
>> M3a = mat; % preallocate output matrix (a).
>> M3b = mat; % preallocate output matrix (b).
>> idi = sub2ind(size(mat),idr,idc); % output linear indices
>> tmp(1,:) = -tmp(1,:); % first row negative (first column of M)
>> mat(idi) = tmp(idx); % assign input values to intermediate matrix
>> idn = sign(mat); % get data signs.
>> [idm,idy] = ismember(abs(mat),M2(:,1)); % find indices of mat in M2.
>> idz = idy(idm);
>> M3a(idm) = M2(idz,2) % allocate M2 to output (a)
M3a =
200 200 0 0 0
0 300 300 300 0
0 0 400 0 400
>> M3b(idm) = M2(idz,3) % allocate M2 to output (b)
M3b =
240 240 0 0 0
0 360 360 360 0
0 0 480 0 480
>> M3 = reshape([M3a.*idn,M3b.*idn].',size(mat,2),[]) % concatenate and reshape
M3 =
200 240 0 0 0 0
-200 -240 300 360 0 0
0 0 -300 -360 400 480
0 0 300 360 0 0
0 0 0 0 400 480

More Answers (1)

Jan
Jan on 23 Apr 2018
Edited: Jan on 23 Apr 2018
Let's call the matrices A, B, C.
B = [ 1 100 120 ; 2 200 240 ; 3 300 360 ; 4 400 480 ];
% Remove the sign at first:
negA = (A < 0);
A = abs(A);
C = zeros(size(A)); % Pre-allocate
odd = rem(1:size(A, 2), 2);
for iB = 1:size(B, 1)
index = (A == B(iB, 1));
C(index & odd) = B(iB, 2);
C(index & ~odd) = B(iB, 3);
end
% Consider the sign:
C(negA) = -C(negA);
  2 Comments
Darrian Low
Darrian Low on 23 Apr 2018
Hey mate, here is my output:
C = [ 100 240 ; 200 360 ; 300 480 ; 100 360 ; 100 480 ]
There must have been an error with the formatting. Since I require 5x6 matrix as the output.
Thanks for your help though. Appreciate it!
Jan
Jan on 23 Apr 2018

This is impossible, when your input "MatrixONE" is a 5x6 matrix. Please post the data such that they can be used by copy&paste. The screenshot is nice, but it cannot be used directly.

A = [ 2,  2,  0,  0, 0, 0; ...
     -2, -2,  3,  3, 0, 0; ...
      0,  0, -3, -3, 4, 4; ...
      0,  0,  3,  3, 0, 0; ...
      0,  0,  0,  0, 4, 4];

With this input I get exactly the wanted output:

C = 200   240     0     0     0     0
   -200  -240   300   360     0     0
      0     0  -300  -360   400   480
      0     0   300   360     0     0
      0     0     0     0   400   480

It seems like you have defined the input as

A = [1,2;2,3;3,4;1,3;1,4]

in opposite to your question.

Sign in to comment.

Categories

Find more on Creating and Concatenating Matrices 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!