I want to create a loop that will iterate over several strings, but unable to do so in Matlab.
What works is:
for i=1:3
if (i==1)
b='cow';
elseif (i==2)
b='dog';
else
b='cat';
end
disp(b);
end
and the result is:
cow
dog
cat
But what I want is something more elegant that will look like:
for i=['cow','dog','cat']
disp (i);
end
and give the same result.
Is there an option in Matlab to do this?
ADDITION:
I need the words as strings later on to use and not just to display (the disp was just as an example). I've tried to use cell arrays in my real program:
clear all;
close all;
clc;
global fp_a
global TEST_TYPE
global SHADE_METHODE
for fp_a=11:24
for shade={'full','fast'}
SHADE_METHODE=shade(1);
for test={'bunny','city'}
TEST_MODE=test(1);
fprintf ('fp_a:%d | test: %s | shade: %s',fp_a,TEST_TYPE,SHADE_METHODE);
ray_tracing;
end
end
end
It doesn't work as the values stay as cells and not strings I get the error message:
??? Error using ==> fprintf Function is not defined for 'cell' inputs.
*-I don't really need the fprintf I just use it to check that the values are correct.
**-ray_tracing is my code that uses the values of the strings
Or you can do:
for i={'cow','dog','cat'}
disp(i{1})
end
Result:
cow
dog
cat
Your problems are probably caused by the way MATLAB handles strings. MATLAB strings are just arrays of characters. When you call ['cow','dog','cat'], you are forming 'cowdogcat' because [] concatenates arrays without any nesting. If you want nesting behaviour you can use cell arrays which are built using {}. for iterates over the columns of its right hand side. This means you can use the idiom you mentioned above; Oli provided a solution already. This idiom is also a good way to showcase the difference between normal and cell arrays.
%Cell array providing the correct solution
for word = {'cow','dog','cat'}
disp(word{1}) %word is bound to a 1x1 cell array. This extracts its contents.
end
cow
dog
cat
%Normal array providing weirdness
for word = ['cow','dog','cat'] %Same as word = 'cowdogcat'
disp(word) %No need to extract content
end
c
o
w
d
o
g
c
a
t
Sure! Use cell arrays for keeping strings (in normal arrays, strings are considered by character, which could work if all strings have the same length, but will bork otherwise).
opts={'cow','dog','cat'}
for i=1:length(opts)
disp(opts{i})
end
Use string arrays which where introduced in R2017a I believe. Note the double-quotes:
for i = ["cow", "dog", "cat"]
disp(i);
end
Related
I've hit some unexpected behaviour using the fprintf() function in MATLAB. I'm trying to print a multi-line file using the contents of a cell array and a numerical array. I know that I can use the fprintf() function as follows to print out the contents of a cell array:
myCellArray = {'one','two','three'};
fprintf('%s\n',myCellArray{:})
This results in the following output:
one
two
three
I can also print out a numerical array as follows:
myNumericalArray = [1,2,3];
fprintf('%i\n',myNumericalArray)
This results in:
1
2
3
However, the weird behaviour appears if I try to mix these, as follows:
fprintf('%s is %i\n',myCellArray{:},myNumericalArray)
This results in:
one is 116
wo is 116
hree is 1
I think this happens because MATLAB tries to print the next entry in myCellArray in the place of the %i, rather than using the first entry in myNumericalArray. This is evident if I type the following:
fprintf('%s %s\n',myCellArray{:},myCellArray{:})
Which results in:
one two
three one
two three
...Is there some way to ensure that only one element from each array is used per line?
I agree with your idea. So, I could only think of circumventing this by creating a combined cell array with alternating values from your two initial arrays, see the following code:
myCombinedArray = [myCellArray; mat2cell(myNumericalArray, 1, ones(1, numel(myNumericalArray)))];
fprintf('%s is %i\n', myCombinedArray{:})
Gives the (I assume) desired output:
one is 1
two is 2
three is 3
fprintf(formatSpec,A1,...,An) will print all the element of A1 in column order, then all the element of A2 in column order... and size(A1) is not necessarily equal to size(A2).
So in your case the easiest solution is IMO the for loop:
for ii = 1:length(myCellArray)
fprintf('%s is %d\n',myCellArray{ii},myNumericalArray(ii))
end
For the small explanation foo(cell{:}) is similar to the splat operator (python, ruby,...) so matlab will interpret this command as foo(cell{1},cell{2},...,cell{n}) and this is why your two arguments are not interpreted pair-wise.
This is similar to the loop solution, only more compact:
arrayfun(#(c,n) fprintf('%s is %i\n', c{1}, n), myCellArray, myNumericalArray)
I want to store an array which changes its size in each iteration of a for loop.
For example,
for y=1:100
for x=1:50
.
.
ms(:,x,y) = ans;
.
.
end
end
The 'ans' is a row vector which changes its size in each iteration of y.
How can i store these variable length 'ans' into ms?
When i try to initialize 'ms' as cell, it shows an error saying "Conversion to cell from double is not possible."
What are the ways i can solve this?
Thanks
Kind regards
The only way I can think of is to indeed use a cell array. Initialize a 2D cell array like so:
ms = cell(50,100);
After, you index into the cell by using curly braces ({}). Therefore, your loop will look like:
for y=1:100
for x=1:50
.
.
ms{x,y} = ans;
.
.
end
end
After you're done, you can index into the cell array by choosing the row and column location you want:
vec = ms{row,col};
BTW, I don't recommend you use ans as a variable. ans is the default variable that is used when you execute a statement in MATLAB which has an output and you don't specify a variable of where this output from the function will go. You may have code that will overwrite the ans variable, so you should perhaps use another name.
One way to do this:
ms = {};
for y=1:100
for x=1:50
ms = [ms 1:x];
% or
% ms = [ms new_cell_element];
end
end
You can also index the cell array with ms{x,y} = 1:3;
new_cell_element does not need to be a cell, it can be anything you want.
ms = [ms, 'A string', (1:5).'] %// Works!
Note that I do not recommend this, and I'm pretty sure there are other ways to do this, depending on what you want to do inside those nested loops. You should check out cellfun, and read up on cells in general.
Also, never ever use ans as a variable name in MATLAB. That will only cause you trouble. Any other name is better (except clear and builtin).
I am trying to use MATLAB in order to generate a variable whose elements are either 0 or 1. I want to define this variable using some kind of concatenation (equivalent of Java string append) so that I can add as many 0's and 1's according to some upper limit.
I can only think of using a for loop to append values to an existing variable. Something like
variable=1;
for i=1:N
if ( i%2==0)
variable = variable.append('0')
else
variable = variable.append('1')
i=i+1;
end
Is there a better way to do this?
In MATLAB, you can almost always avoid a loop by treating arrays in a vectorized way.
The result of pseudo-code you provided can be obtained in a single line as:
variable = mod((1:N),2);
The above line generates a row vector [1,2,...,N] (with the code (1:N), use (1:N)' if you need a column vector) and the mod function (as most MATLAB functions) is applied to each element when it receives an array.
That's not valid Matlab code:
The % indicates the start of a comment, hence introducing a syntax error.
There is no append method (at least not for arrays).
Theres no need to increment the index in a for loop.
Aside of that it's a bad idea to have Matlab "grow" variables, as memory needs to be reallocated at each time, slowing it down considerably. The correct approach is:
variable=zeros(N,1);
for i=1:N
variable(i)=mod(i,2);
end
If you really do want to grow variables (some times it is inevitable) you can use this:
variable=[variable;1];
Use ; for appending rows, use , for appending columns (does the same as vertcat and horzcat). Use cat if you have more than 2 dimensions in your array.
How can I insert strings in an array while looping in MATLAB? I know it's very simple but I get a mismatch error. Here is sample code.
s={'asd', 'xyzs', 'pqrs','mnopr'};
for i=1:4
w=randint(1,1,[1,2]);
switch w
case 1
word(i)=s(i);
otherwise
word(i)=3;
end
end
Your problem is that s is a cell and word is not. There are many things you can do to fix this, but an easy way would be to define word to be a cell of size(s). You would then have to convert any numbers into cells before inserting them, which means that your code would look like this:
s={'asd','xyzs','pqrs','mnopr'};
word = cell(size(s));
for i=1:4
w=randint(1,1,[1,2]);
switch w
case 1:
word(i)=s(i);
otherwise
word(i)= num2cell(3);
end
end
hi let's assume i have the following in matlab
h = [0,0,0,1;
1,1,1,1];
now how can i print all the values of the first subarray, i.e. 0,0,0,1
or for example the second subarray 1,1,1,1. thanks !
You can access just the first row of your matrix by doing
firstRow = h(1,:)
Similarly, you could access just the third column by
thirdColumn = h(:,3)
I suggest you look into the MATLAB help under "Matrix Indexing" as this is really basic stuff (and there's a lot of other nifty things you can do to access a subset of a matrix)
For printing, you can omit the final ;, or look into functions display and fprintf.