Save output from multiple loops matlab - matlab

Hello I have 3 variables i,j and k. I want to run a loop on each of them such that for each value of i, one value of j is considered and iterated over all values of k.Then for same i, take second value of j and iterate over all values of k and so on... Then repeat this process for all the values of i and save the output. For example for i=1,j=1 iterate over all values of k.Then for i=1, j=2 iterate over all values of k so on. Then save the output m for all the values of i and j over k iterations.
for i=1:30
for j=1:5
for k=1:100
m=i*0.5*j*sin(k);
end
end
end
May be my code is not right as well?

Using ndgrid you can accomplish this without any explicit for loops:
[i,j,k] = ndgrid(1:30,1:5,1:100);
m = 0.5*i.*j.*sin(k);
Or with meshgrid if you flip the first two inputs:
[j,i,k] = meshgrid(1:5,1:30,1:100);
m = 0.5*i.*j.*sin(k);

The easiest thing you can do is to define m as a 3D array; also, since you know in advance the final size of the array you can initialize it before the loops to avoid MatLab allocating the memory at each iteration:
% Initialize the array
m=zeros(30,5,100);
for i=1:30
for j=1:5
for k=1:100
% Set the values in the array "m"
m(i,j,k)=i*0.5*j*sin(k);
end
end
end
EDIT
In case you want, for each i and j the value of m be computed over k iterations, the variable m should be present also on the right of the = sign.
It should, for example, be somenthing like:
m=m+i+j+k
you can try the following modified version of the above code
% Initialize the array
m=zeros(30,5);
for i=1:30
for j=1:5
% Initialize the temporary varaible at each iteration
tmp_var=0;
for k=1:100
% Compute the value of "tmp_var" over "k" iteration
tmp_var=tmp_var+i*0.5*j*sin(k);
end
% Assign the value of "tmp_var" computed for a given (i,j) couple
m(i,j)=tmp_var;
end
end
In this example you need to define a temporary varaible to be used inside the k loop; at the end of the k loop the value of the temporary variable will be stored in the m matrix.
At the end of the script, you will have a matrix m of size (30 x 5).
Hope this helps.

In cases where the computation in the loop is only depending on the loop index you could just write:
[j,i,k]=meshgrid(1:5,1:30,1:100);
m=.5*i.*j.*sin(k);
meshgrid will create the appropriate 3D arrays of the indices i,j,k and m will be of the same dimension when the elementwise multiplication (.* instead of *) is used.

Related

MATLAB: how do I create a vector where each element is a function of the previous element

Working in Matlab.
I am trying to create a vector where each element is a function of the previous element. The goal is to put the first 50 (or so) values of a logistical function in a vector. So I start with 0.200, with r=4 (for example), the second element would then be 40.200(1-0.200)=0.640.
The third element would take the value 0.64 and perform the same function on that number, and so on...
I have tried a for-loop, but since there is no counter in the function, the loop doesn't work.
EDIT: I have created the following function:
n = 0;
x = 0.200;
for n=0:100
x=4*x*(1-x)
n=n+1
end
This gives the first 100 values. But I fail to get them as values in a vector...
Any suggestions on how to solve this would be appreciated.
You need to use indexing for the x vector you are creating. The way you currently have it coded, everything is going into a scalar x and not a vector x. E.g.,
n = 50; % the number of elements you want to fill
x = zeros(1,n); % allocate a vector to hold the numbers
x(1) = 0.200; % set the first value
for k=2:n % loop through the remaining values
x(k) = 4*x(k-1)*(1-x(k-1)); % set the next value using the previous value
end
Note that in the above code all of the usages of x other than the initial allocation involve indexing, e.g. x(1) and x(k) and x(k-1).

storing values from a matrix to another one with an if operation using matlab

I have a "x1" matrix, and I want to extract some particular elements with respect to a logical condition:
for z=1:length(x1)
if (x1(z+1)-x1(z))>=20)
extract=
end
end
How can I obtain the "extract" matrix and the indices of these values in x1?
The index of the elements in x1 is obviously z itself: the z-th element satisfies that condition. In extract I suppose you want to put x1(z), so that's the value. But extract may have less elements than x1 so we need a proper index to run through extract, let's call it k.
k=1
for z=1:length(x1)-1
if (x1(z+1)-x1(z))>=20)
extract(k)=x1(z); %if you want to extract the value
k=k+1;
end
end
or, if you want to save the index of x1 and not the value
k=1
for z=1:length(x1)-1
if (x1(z+1)-x1(z))>=20)
extract(k)=z;
k=k+1;
end
end
At the end of this loop, extract will be an array containing all the values (first loop) or the indices (second loop) of the elements in x1 that satisfy your condition.
For the sake of completeness, to obtain both, we must engage two arrays (extract for the values and indices for the indices):
k=1
for z=1:length(x1)-1
if (x1(z+1)-x1(z))>=20)
extract(k)=x1(z); % store the value
indices(k)=z; % store the index
k=k+1;
end
end
You can use this code to extract the indices
x1Diff = diff(x1)
x1DiffTh = zeros(size(x1Diff))
x1DiffTh[x1Diff>20] = 1
indx = find(x1DiffTh)
Or compacted in 1 line
indx = find(diff(x1)>20)
For loops are very ineficient in Matlab since the code is not compiled.

Saving data generated at each iteration in multidimensional array in MATLAB

I have this code:
for h= 1:length ( bb1{CH(i)})
for k= 1:length( bb2{CH(j)})
if NN(bb1{CH(i)}(h),bb2{CH(j)}(k))==1
d = [bb1{CH(i)}(h),bb2{CH(j)}(k)]
end
end
end
When I run this code, the value of d takes the value of the last iteration. I want to save its value for all the iterations. For example, I want to have a rows_nb by 2 matrix.
This is highly unoptimized code, but the reason is pretty obvious. Your code is assigning to d at every iteration in that code and it keeps overwriting itself.
As such, you need to append to d if you want to save all of the values in the matrix. Therefore, do this:
for h= 1:length ( bb1{CH(i)})
for k= 1:length( bb2{CH(j)})
if NN(bb1{CH(i)}(h),bb2{CH(j)}(k))==1
d = [d; bb1{CH(i)}(h),bb2{CH(j)}(k)]; %// Concatenate
end
end
end
This way, you are adding two columns every time to the matrix and add an additional row at each iteration.

expand matrix in matlab?

I would like to expand matrix row by row under a conditional statement without initializing the matrix. In C++, simply I use std::vector and push_back method without initializing the size of the vector in C++. However, I want to do same scenario in Matlab. This is my pseudo code
for i = 1:lengt(data)
if ( condition )
K = [data(1) data(2) i]
end
K
Let us assume some working code to resemble your pseudo-code.
%// Original code
for i = 1:10
if rand(1)>0.5
data1 = rand(2,1)
K = [data1(1) data1(2) i]
end
end
Changes for "pushing data without initialization/pre-allocation":
To save data at each iteration we keeping on "stacking" data along a chosen dimension. This could be thought of as pushing data. For a 2D case, use either a "row vector push" or a "column vector push". For this case we are assuming a former case.
We don't index into K using the original iterator, but use a custom one,
that only increments when the condition is satisfied.
The code below must make it clear.
%// Modified code
count = 1; %// Custom iterator; initialize it for the iteration when condition would be satisfied for the first time
for i = 1:10
if rand(1)>0.5
data1 = rand(2,1)
K(count,:) = [data1(1) data1(2) i] %// Row indexing to save data at each iteration
count = count +1; %// We need to manually increment our custom iterator
end
end
If we assume from the above that data is an Nx2 matrix, and that you only want to save the rows that satisfy some condition, then you almost have the correct code to update your K matrix without having to initialize it to some size:
K = []; % initialize to an empty matrix
for i=1:size(data,1) % iterate over the rows of data
if (condition)
% condition is satisfied so update K
K = [K ; data(i,:) i];
end
end
K % contains all rows of data and the row number (i) that satisfied condition
Note that to get all elements from a row, we use the colon to say get all column elements from row i.

In an assignment A(I) = B, the number of elements in B and I must be the same

Now, I understand the problem here, what I don't understand however is that how should 'I' be initialized??
For instance, in my case variable 'p' generates an array at the end of every for loop, which is programmed to run for 101 times. The output of p looks something like this
p =
-0.0149 -0.0149
Now, I want to store this value into another variable at the end of every for loop and increment its index.
So,What should be the dimension of that variable?
I have tried initializing ---> A=rand(2,101);
If you don't wish to pre-allocate the array A. Then you can keep appending the values in A at the each for loop iteration as follows:
A=[];
for loop
get p vector (every iteration it should be 2x1)
A=[A p];
end
Or you can directly write in the for loop:
A(:,i)=p; %but your p vector seems to be 1x2 and not 2x1. If it is 2x1, then you should initialize A as rand(101,2)