I am relatively new to matlab, and I was wondering if there was a simpler way to do the following:
Given mycellarray = {[1 2 3 4] [5 6 7 8] [9 10 11 12] [13 14 15 16]}, I would like to assign each matrix inside mycellarray to a separate variable. Is there any faster/better/shorter way to do it than this?
a = cell2mat(mycellarray(1,1))
b = cell2mat(mycellarray(1,2))
c = cell2mat(mycellarray(1,3))
d = cell2mat(mycellarray(1,4))
Thanks in advance!
[a,b,c,d]=mycellarray{:}
The {:} makes a comma seperated list of the cell array, which an be assigned to individual variables.
relevant documentation pages:
colon operator
comma seperated list
Here a short example on how to do what you want with the MATLAB function deal.
a = {[1 2 3] [4 5 6] [7 8 9]}
[aa bb cc] = deal(a{:})
Related
I am having difficulty concatenating vectors in MATLAB.
A = [1
2
3]
B = [6
7
8
9
10]
Desired result:
C = [1
2
3
6
7
8
9
10]
where the sizes of A and B are different in every iteration of my script and I want to form the concatenated resulting vector, C, which has a dynamic size.
This is what I have tried:
A = [1
2
3];
B = [6
7
8
9
10];
Vertical concatenation of two vectors/matrices is what you want, done like this...
C = [A; B];
... or this...
C = [A
B];
... or this...
C = vertcat(A,B);
All three of these give
C = [1
2
3
6
7
8
9
10]
% As you requested...
You were running into trouble because you were trying to use horzcat
C = horzcat(A',B');
Horizontal concatenation merges matrices horizontally, i.e.
C = [1, 6
2, 7
3, 8
?, 9
?, 10]
So to avoid this, you've transposed the matrices to make them rows instead of columns, then transposed the result back?? You just need vertcat! I have shown the shorthand and full form for this above.
Try:
A = [1 2 3];
B = [4 5 6 7 8 9 10];
C = [A B]
For vertical vectors A' and B' use:
C = [A;B]
The fool-proof way is this:
C = [A(:);B(:)];
If you use this method then it does not matter if A and B are row vectors, column vectors, or even matrices.
Say we want to concatenate two matrices
a=[2 3 6] , b=[0 9 3 2 8 2]
but we don't want any repetitive elements in the concatenated matrix.
in other words we want c to be
c=[2 3 6 0 9 8]
Is there a built-in function that does that for us?
% You could use the union function to accomplish this
a = [2 3 6]; % array a
b = [0 9 3 2 8 2]; % array b
% Use the union function to concatenate a and b. It lists an item that appears in either array once.
c = union(a,b, 'stable'); % adding 'stable' keeps your current order
I got a 4-by-n matrix, like
A =
1 5 9
3 0 6
2 3 10
7 8 4
What I want to do with A is getting each half column of A as
Line1Point1 = [1 3]
Line1Point2 = [2 7]
Line2Point1 = [5 0]
Line2Point2 = [3 8]
Line3Point1 = [9 6]
Line3Point2 = [10 4]
How could I do that? I’m pretty new to matlab coding.. Any help is really appreciated..
Cheers
Use reshape function, for example:
>> A = [1 5 9;
3 0 6;
2 3 10;
7 8 4];
>> reshape(A,2,6)
ans =
1 2 5 3 9 10
3 7 0 8 6 4
Storing such information as many variables is generally a bad idea
Some options for storing and accessing are
Cell array
Line=mat2cell(A,[2,2],ones(1,size(A,2))).'
access with
Line{2,1}
ans =
5
0
Indexing
as other answers
Anonymous Function
Line=#(l,p)A(2*p-1:2*p,l)
access with
Line(2,1)
ans =
5
0
Structure
Not really a useful solution, more for interests sake
for ii=1:size(A,2);for jj=1:2;Line(ii).Point(jj).Value=A(2*jj-1:2*jj,ii);end;end
access with
Line(2).Point(1).Value
ans =
5
0
A(1:2,1) will give you first half of the first column.
A(3:4,1) will give you second half of the first column.
A(1:2,2) will give you first half of the second column.
A(3:4,2) will give you second half of the second column.
A(1:2,3) will give you first half of the third column.
A(3:4,3) will give you second half of the third column.
You can create the variables with the eval function, which executes the input string. Using eval is commonly regarded as bad practice since it is horrible to debug.
Nevertheless, here's the code:
A = [1 5 9; 3 0 6; 2 3 10; 7 8 4];
for ii = 1:length(A(1,:))
eval(['Line' num2str(ii) 'Point1 = A(1:2, ii)' ]);
eval(['Line' num2str(ii) 'Point2 = A(3:4, ii)' ]);
end
% Now all variables are created - for example: Line2Point1
A more elegant solution could be to store the vectors in a cell array. You can acces the first vectors for example by typing: c{1,1}
c = cell(length(A(1,:)),2)
for ii = 1:length(A(1,:))
c{ii,1} = A(1:2, ii);
c{ii,2} = A(3:4, ii);
end
I would suggest using 3D arrays to store and then access those values.
Code
N = size(A,1)/2;
LinePoint = permute(reshape(A,N,size(A,1)/N,[]),[1 3 2])
Here,
2nd dimension indices (columns) would represent Line IDs
3rd dimension indices would represent Point IDs.
Thus, the representative 3D array would be - LinePoint(:,LineID,PointID).
Example run
For your given A, we would have LinePoint as -
LinePoint(:,:,1) =
1 5 9
3 0 6
LinePoint(:,:,2) =
2 3 10
7 8 4
Thus,
Line1Point1 would be denoted by LinePoint(:,1,1)
Line1Point2 would be denoted by LinePoint(:,1,2)
Line2Point1 would be denoted by LinePoint(:,2,1)
Line2Point2 would be denoted by LinePoint(:,2,2)
Line3Point1 would be denoted by LinePoint(:,3,1)
Line3Point2 would be denoted by LinePoint(:,3,2)
Imagine I have a cell array "list of lists" in Octave:
octave:6> a = {[1], [3,4], [5,6,7], [8,9,10,11]}
a =
{
[1,1] = 1
[1,2] =
3 4
[1,3] =
5 6 7
[1,4] =
8 9 10 11
}
Now I want to extract a given element from each of the nested rows and the index of each of them is given in a list. E.g. [1, 2, 2, 3] would mean return [1, 4, 6, 10].
What is the best Octave-ish way to do this? I know how to do that with a loop, but that seems ugly...
It seems I have found the solution that is good to me. I realized that cellfun() takes a number of arguments so I can perform the element-wise mapping easily.
octave:31> cellfun(#(x,y) x(y), a, {1,2,2,3})
ans =
1 4 6 10
>> [1 2]
ans =
1 2
>> [1 ,2]
ans =
1 2
>>
It looks the same,is that true?
Nope; there's no difference. See here for more info:
The simplest way to create a matrix in
MATLAB is to use the matrix
constructor operator, []. Create a row
in the matrix by entering elements
(shown as E below) within the
brackets. Separate each element with a
comma or space:
row = [E1, E2, ..., Em] row = [E1 E2 ... Em]
Both produce a row vector when applied to scalar elements, i.e., horizontal concatenation. A space is equivalent to a comma inside square brackets to construct an array or vector. In fact, you can use spaces and commas at will within such an expression, although this may be best not done as it will be confusing to read. For example, this is difficult for me to read:
A = [1 2,3, 4 , 5 6 7, 8]
Far easier to read is either one of these alternatives:
A = [1 2 3 4 5 6 7 8]
A = [1,2,3,4,5,6,7,8]
Had you separated the elements with ; instead, this would produce vertical concatenation, which is a different animal. You can also build up arrays using these separators. So to create a 2x3 array,
A = [1 2 3;4 5 6]
A =
1 2 3
4 5 6
If you have doubt in the future test it by ISEQUAL function:
>> a=[1 2];
>> b=[1,2];
>> isequal(a,b)
ans =
1