How to take the median of the following a 4D array (31x6x2x3)? - arrays

I am trying to get the median of each row of the same columns of the following 4D array:
df = randn(31,6,2,3)
What I basically have is 31 rows (i) of 6 variables (j) for two shocks (k), all this repeated 3 times (n). Now, focus on the first shock and get a 31x6x3 array:
eg1 = squeeze(df(:,:,1,:)) %31x6x3
What I want to get is the median of every row of the same column: e.g. the first row of the first column of the 3 repetitions, then the second row of the first column of the 3 repetitions, etc. Easier to see like this:
% median of every row of the first column in the 3 repetitions
median(eg1(1,1,:))
median(eg1(2,1,:))
median(eg1(3,1,:))
...
median(eg1(31,1,:))
% median of every row of the second column in the 3 repetitions
median(eg1(1,2,:))
median(eg1(2,2,:))
median(eg1(3,2,:))
...
median(eg1(31,2,:))
% basically the median of every row of the same column for every column
This shall be done for either shocks 1 and 2.
Can anyone help me with this?

What you want is the median of the last dimension. median accepts desired dimension as input.
out=median(eg1,3)
out will be a 31x6 matrix.
If you want that from all of the egx, you just want the median of the last dimension
out=median(df,4)

Related

how to create array of random normalize number?

i want to create a matrix that each row of the matrix have 7 real random number in [0,1] and the sum of number in each rows should be equal to 1.
this matrix have 100 rows and 7 columns. how can i do it?
at first ,i create an array with 1 row and 7 columns. then write the code as bellow. i try normal the number in the rows but sum of each row became more than 1.how can i fix it? thank for taking your time.
a = rand(1,7);
for i=1:7
a(i) = a(i)/sum(a);
end
sum(a)
For 100 by 7, you can use bsxfun:
a = rand(100,7);
a = bsxfun(#rdivide,a.',sum(a.')).';
Here the sum of each row = 1
The problem is that by using a for-loop, you're changing the sum of the vector every loop iteration. You should take advantage of MATLAB's ability to act on whole matrices at once:
a = rand(1,7);
a = a./sum(a);

Matlab: Extracting the entire row of a max value in a matrix

I have a matrix with six columns. I found the max value of a certain column but how would I go about extracting the entire row pertaining to that value?
To extract row 1 of matrix A use A([1],:) to extract row 1 and 2 use A([1,2],:)
Use the max() function as explained here. For example
if A is your matrix
[M, I] = max(A)
Row = A([I(1)],:)
where I(1) is used to find the row containing the max element of the first coloumn

Excel average rows to array formula

I want to take the average of rows which would result in a column (array). Example input:
3 4
4 4
4 6
With an array formula I want to create:
3.5
4
5
The average is the sum of numbers divided by the count of that numbers.
So first add them (A1:A3+B1:B3)
3+4 = 7
4+4 = 8
4+6 = 10
Then divide by the number of numbers(/2):
7/2 = 3.5
8/2 = 4
10/2 = 5
{=(A1:A3+B1:B3)/2}
edit after comment from op:
formula for addition without adding column manually from https://productforums.google.com/forum/#!topic/docs/Q9x44sclzfY
{=mmult(A1:B3,sign(transpose(column(A1:B3))))/Columns(A1:B3)}
This is one way to do that in Excel
=SUBTOTAL(1,OFFSET(A1:B3,ROW(A1:B3)-MIN(ROW(A1:B3)),0,1))
OFFSET supplies an "array of ranges", each range being a single row, and SUBTOTAL with 1 as first argument, averages each of those ranges. You can use this in another formula or function or entered in a range on the worksheet.
The advantage over Siphor's suggestion with MMULT is that this will still work even with blanks or text values in the range (those will be ignored)
If first column is A and the second is B, then enter this formuls in column C:
=AVERAGE(A1,B1)
and extend it to the last row
Also you can use a range if you have more than 2 columns (this function allows for some cells to be empty):
=AVERAGE(A1:F1)

MATLAB Efficiently find the row that contains two of three elements in a large matrix

I have a large matrix, let's call it A, which has dimension Mx3, e.g. M=4000 rows x 3 columns. Each row in the matrix contains three numbers, eg. [241 112 478]. Out of these three numbers, we can construct three pairs, eg. [241 112], [112 478], [241 478]. Of the other 3999 rows:
For each of the three pairs, exactly one row of M (only one) will contain the same pair. However, the order of the numbers could be scrambled. For example, exactly one row will read: [333 478 112]. No other row will have both 478 and 112. I am interested in finding the index of that row, for each of the three pairs. The output should then be another matrix, call it B, with same dimensions 4000x3, where each row has the indices of the rows in the original matrix A that share a pair of numbers.
No other row will contain the same three numbers.
Other rows may contain none of the numbers or one of the numbers.
Here's a function that accomplishes this, but is very slow - I'd like to know if there is a more efficient way. Thanks in advance!
M=size(A,1); % no elements
B=zeros(M,3);
for j=1:M
l=1;
k=1;
while l<4 % there cant be more than 3
if k~=j
s=sum(ismember(A(j,:),A(k,:)));
if s==2
B(j,l)=k;
l=l+1;
end
end
k=k+1;
end
For loops are not needed, just use ismember the following way:
row_id1=find(sum(ismember(M,[241 112]),2)>1);
row_id2=find(sum(ismember(M,[478 112]),2)>1);
row_id3=find(sum(ismember(M,[478 241]),2)>1);
each row_id will give you the row index of the pair in that line regardless of the order at which it appears.
The only assumption made here is that one of the pair numbers you look for will not appear twice in a row, (i.e. [112 333 112]). If that assumption is wrong, this can be addressed using unique.

finding index of rows in matlab

i have a matrix B of N*3 dim. I want to find the indices of B whose column 3 has value 1.
I used the command [~,id]=ismember(1,B(:,3)). id returns only value 1 even though there are many rows in the matrix which has the column 3 with value 1. Can any one point out what is wrong in the command?
Rather do:
id = find(B(:,3)==1)
but as an aside, to use ismember you should swap your input [~,id]=ismember(B(:,3),1).

Resources