how to change size(out) = [m n] in matlab - matlab

This is a continuation of my previous problem, so now i want to know how to change array size and how to use size(out) = [m n].
so basically if you have 10x10 array and you want to plot column 9 vs. column 10 in scatter plot, and you want column 1-column 8 to be the labels of your scatter plot. how can i use size(out) = [10 10]?
for someone who want examples:
Auto-Label in scatter plot using matlab
and what if your array is m x n? is there a general code for this? please enlighten me, thanks.

To make things more general you can make use of the end keyword, which refers to the last row/column or an array/cell array/anything in Matlab (actually "last array of index").
Revisiting your example, you could use num2str (alternatively to sprintf) and use the following:
scatter(out(:,end-1), out(:,end));
for k = 1:size(out,1)
T{k} = num2str(out(k,1:end-2));
end
xshift = 0.03; yshift = 0.03;
text(out(:,3)+xshift, out(:,4)+yshift, T);
grid on
Which gives this:

Related

Indexing sections to plot in a MATLAB for loop

I have a matlab indexing question. I have a vector of 34 elements that I would like to plot in a for loop. However, I do not wish to plot them all at once. It would be great if I were able to plot elements 1:6, then 7:11, then 12:20, and so on. Is it possible to do this type of plotting in a for loop? If it is, I am having trouble with the indexing. Since these elements are all in sequential order, matlab seems to want to plot them all together. Any help would be appreciated. Thanks!
Here is an example of what I am trying to do:
for i = 1: [1:6, 7:11, 12:20]
plot(x(i), y(i))
end
Hopefully, I can get three plot, one with data from elements 1:6, another from elements 7:11, and the last one from elements 12:20.
You can just use a cell to store the variable-length vectors containing the various indices:
x = linspace(0, 1, 20);
y = x;
i_cell = {1:6, 7:11, 12:20};
for i = 1:length(i_cell)
figure
indices = i_cell{i}
plot(x(indices), y(indices))
end

Plot a cell into a time-changing curve

I have got a cell, which is like this : Data={[2,3],[5,6],[1,4],[6,7]...}
The number in every square brackets represent x and y of a point respectively. There will be a new coordinate into the cell in every loop of my algorithm.
I want to plot these points into a time-changing curve, which will tell me the trajectory of the point.
As a beginner of MATLAB, I have no idea of this stage. Thanks for your help.
Here is some sample code to get you started. It uses some basic Matlab functionalities that you will hopefully find useful as you continue using it. I added come data points to you cell array for illustrative purposes.
The syntax to access elements into the cell array might seem weird but is important. Look here for details about cell array indexing.
In order to give nice colors to the points, I generated an array based on the jet colormap built-in in Matlab. Basically issuing the command
Colors = jet(N)
create a N x 3 matrix in which every row is a 3-element color ranging from blue to red. That way you can see which points were detected before other (i.e. blue before red). Of course you can change that to anything you want (look here if you're interested).
So here is the code. If something is unclear please ask for clarifications.
clear
clc
%// Get data
Data = {[2,3],[5,6],[1,4],[6,7],[8,1],[5,2],[7,7]};
%// Set up a matrix to color the points. Here I used a jet colormap
%// available from MATLAB but that could be anything.
Colors = jet(numel(Data));
figure;
%// Use "hold all" to prevent the content of the figure to be overwritten
%// at every iterations.
hold all
for k = 1:numel(Data)
%// Note the syntax used to access the content of the cell array.
scatter(Data{k}(1),Data{k}(2),60,Colors(k,:),'filled');
%// Trace a line to link consecutive points
if k > 1
line([Data{k-1}(1) Data{k}(1)],[Data{k-1}(2) Data{k}(2)],'LineStyle','--','Color','k');
end
end
%// Set up axis limits
axis([0 10 0 11])
%// Add labels to axis and add a title.
xlabel('X coordinates','FontSize',16)
ylabel('Y coordinates','FontSize',16)
title('This is a very boring title','FontSize',18)
Which outputs the following:
This would be easier to achieve if all of your data was stored in a n by 2 (or 2 by n) matrix. In this case, each row would be a new entry. For example:
Data=[2,3;
5,6;
1,4;
6,7];
plot(Data(:, 1), Data(:, 2))
Would plot your points. Fortunately, Matlab is able to handle matrices which grow on every iteration, though it is not recommended.
If you really wanted to work with cells, there are a couple of ways you could do it. Firstly, you could assign the elements to a matrix and repeat the above method:
NumPoints = numel(Data);
DataMat = zeros(NumPoints, 2);
for I = 1:NumPoints % Data is a cell here
DataMat(I, :) = cell2mat(Data(I));
end
You could alternatively plot the elements straight from the cell, though this would limit your plot options.
NumPoints = numel(Data);
hold on
for I = 1:NumPoints
point = cell2mat(Data(I));
plot(point(1), point(2))
end
hold off
With regards to your time changing curve, if you find that Matlab starts to slow down after it stores lots of points, it is possible to limit your viewing window in time with clever indexing. For example:
index = 1;
SamplingRate = 10; % How many times per second are we taking a sample (Hertz)?
WindowTime = 10; % How far into the past do we want to store points (seconds)?
NumPoints = SamplingRate * WindowTime
Data = zeros(NumPoints, 2);
while running
% Your code goes here
Data(index, :) = NewData;
index = index + 1;
index = mod(index-1, NumPoints)+1;
plot(Data(:, 1), Data(:, 2))
drawnow
end
Will store your data in a Matrix of fixed size, meaning Matlab won't slow down.

matlab plotting a family of functions

Generate a plot showing the graphs of
y=(2*a+1)*exp(-x)-(a+1)*exp(2*x)
in the range x ∈ <-2, 4> for all integer values of a between -3 and 3
I know how to make typical plot for 2 values and set a range on the axes, but how to draw the graph dependent on the parameter a?
To elaborate on Ben Voigt's comment: A more advanced technique would be to replace the for-loop with a call to bsxfun to generate a matrix of evaluations of M(i,j) = f(x(i),a(j)) and call plot with this matrix. Matlab will then use the columns of the matrix and plot each column with individual colors.
%%// Create a function handle of your function
f = #(x,a) (2*a+1)*exp(-x)-(a+1)*exp(2*x);
%%// Plot the data
x = linspace(-2, 4);
as = -3:3;
plot(x, bsxfun(f,x(:),as));
%%// Add a legend
legendTexts = arrayfun(#(a) sprintf('a == %d', a), as, 'uni', 0);
legend(legendTexts, 'Location', 'best');
You could also create the evaluation matrix using ndgrid, which explicitly returns all combinations of the values of x and as. Here you have to pay closer attention on properly vectorizing the code. (We were lucky that the bsxfun approach worked without having to change the original f.)
f = #(x,a) (2*a+1).*exp(-x)-(a+1).*exp(2*x); %// Note the added dots.
[X,As] = ndgrid(x,as);
plot(x, f(X,As))
However for starters, you should get familiar with loops.
You can do it using a simple for loop as follows. You basically loop through each value of a and plot the corresponding y function.
clear
clc
close all
x = -2:4;
%// Define a
a = -3:3;
%// Counter for legend
p = 1;
LegendText = cell(1,numel(a));
figure;
hold on %// Important to keep all the lines on the same plot.
for k = a
CurrColor = rand(1,3);
y= (2*k+1).*exp(-x)-(k+1).*exp(2.*x);
plot(x,y,'Color',CurrColor);
%// Text for legend
LegendText{p} = sprintf('a equals %d',k);
p = p+1;
end
legend(LegendText,'Location','best')
Which gives something like this:
You can customize the graph as you like. Hope that helps get you started!

Plot eigen Vector e1 & e2 in matlab?

How to be able plot eigen vector in Matlab an make it sure have the exact position as a new axes of our data??
here is my code for PCA
a= randn(100,3);
b=mean(a);
c=cov(a);
[vec,val] = eigs(c);
e1=vec(:,1);
e2=vec(:,2);
plot3(a(:,1),a(:,2),a(:,3),'ro');
hold on
%% Here is the Problem begins
plot(e1,'k--');
plot(e2,'k--');
Here is the output that I got
That two lines represent the e1&e2.
How to plot the e1 & e2 properly???
You can use the output from eig to directly plot all three eigenvectors (or a subset):
a = randn(100,3);
b = mean(a);
c = cov(a);
[vec,val] = eig(c);
plot3(a(:,1),a(:,2),a(:,3),'ro');
hold on
z = zeros(1,3);
% plot3([z(1:2);vec(1,1:2)],[z(1:2);vec(2,1:2)],[z(1:2);vec(3,1:2)],'k')
plot3([z;vec(1,:)],[z;vec(2,:)],[z;vec(3,:)],'k')
axis equal
grid on
And if you want the scaled eigenvectors:
sc_vec = vec*val;
z = zeros(1,3);
plot3([z;sc_vec(1,:)],[z;sc_vec(2,:)],[z;sc_vec(3,:)],'b')
Another option is to use quiver3 to get lines with arrowheads:
scale = 1;
z = zeros(1,3);
quiver3(z,z,z,vec(1,:),vec(2,:),vec(3,:),scale,'g')
Just don't expect the arrows to always look perfect, because Matlab isn't particularly good at this sort of thing.
Note that eig may return the eigenvalues and -vectors in a different order than eigs, but it is the function that you should be using. eigs is a specialized function that solved the eigenproblem in a different way and is much less efficient.
You can use plot3
a= randn(100,3);
b=mean(a);
c=cov(a);
[vec,val] = eigs(c);
e1=[zeros(size(vec(:,1))),vec(:,1)]'; e1 = e1/norm(e1)*4;
e2=[zeros(size(vec(:,2))),vec(:,2)]'; e2 = e2/norm(e2)*4;
e3=[zeros(size(vec(:,3))),vec(:,3)]'; e3 = e3/norm(e3)*4;
plot3(a(:,1),a(:,2),a(:,3),'ro');
hold on
%% Here is the Problem begins
plot3(e1(:,1),e1(:,2),e1(:,3),'k','LineWidth',2);
plot3(e2(:,1),e2(:,2),e2(:,3),'b','LineWidth',2);
plot3(e3(:,1),e3(:,2),e3(:,3),'g','LineWidth',2);
To represent each vector, use plot3 to plot a line from the origin to the coordinates defined by the vector, perhaps multiplied by a large number (I use 10 in the example) to make the line longer:
plot3(10*[0 e1(1)], [0 e1(2)], [0 e1(3)],'b--');
plot3(10*[0 e2(1)], [0 e2(2)], [0 e2(3)],'g--');
You may need to change the view to get a good perspective. For that you can use view function, or click the "Rotate 3D" icon (circular arrow) in the figure toolbar.

plotting diffrent curves in one plot in matlab

I want to make a plot in Matlab like this.
How could I do something like this in Matlab?
Thank you all!
Make some data:
x = 1:0.1:100;
y = 1:5;
for i = y
z(i,:) = sin(i*x);
end
Plot it:
figure
hold on
for i = y
plot3(x,i*ones(size(x)),z(i,:))
end
Modify the plot aspect and view:
daspect([100,2,2])
view(45,60)
Does that do roughly what you need?
You can use the command plot3(X,Y,Z).
You have to build three matrices each one containing a number of column equal to the number of series you need. (6 in the figure you sent)
For example
X = repmat([-200:200]',1,6);
Z = rand(401,6)*10;
Y = ones(401,1)*[1:20:120];
plot3(X,Y,Z)
axis image