How to use print command with loops in Matlab - matlab

I have looked up this simple question regarding printing graphs in Matlab without success so far. I have a for loop of this type:
N = 5;
for sim = 1:10
X = randn(sim,N);
X = mean(X);
figure;
plot(X);
print -depsc X;
end
I would like to print and save one new graph for each simulation, and automatically name it, for example, X1 for sim = 1, X2 for sim = 2, X3 for sim = 3, etc. How do I do this?

Try this:
N = 5;
for sim = 1:10
X = randn(sim,N);
X = mean(X);
hFig = figure;
plot(X);
% create filename and print to eps
filename = strcat('X',num2str(sim));
print(hFig,filename,'-depsc');
end
Hope this helps!

Related

Problem plotting 2d numerical solution of wave equation

I am trying to make an animation of the 2d wave equation in MATLAB (R2020a). So far I believe that the finite difference method is implemented correctly. However; when I try to plot these values using the "surf" command in matlab it does not work.
This is my script so far:
clear
clc
close all
VL = 2;
tMin = 0;
tMax = 30;
xMin = -10;
xMax = 10;
yMin = -10;
yMax = 10;
Nt = 100;
Nx = 100;
Ny = 100;
t = linspace(tMin,tMax,Nt);
x = linspace(xMin,xMax,Nx);
y = linspace(yMin,yMax,Ny);
DeltaT = t(2) - t(1);
DeltaX = x(2) - x(1);
DeltaY = y(2) - y(1);
CFX = ((VL)*(DeltaT/DeltaX))^2;
CFY = ((VL)*(DeltaT/DeltaY))^2;
u = zeros(Nt,Nx,Ny);
[X,Y] = meshgrid(x,y);
u(1,:,:) = Initial(t(1),X,Y);
u(2,:,:) = Initial(t(1),X,Y) + InitialV(t(1),X,Y);
for i=3:Nt
for j=1:Nx
for k=1:Ny
if(j==1 || j==Nx || k==1 || k==Ny)
u(i,j,k) = 0;
else
u(i,j,k) = 2*u(i-1,j,k) - u(i-2,j,k) + (CFX)*(u(i-1,j+1,k) - 2*u(i-1,j,k) + u(i-1,j-1,k)) + (CFY)*(u(i-1,j,k+1) - 2*u(i-1,j,k) + u(i-1,j,k-1));
end
end
end
end
the functions: Initial and initialV are u(0,x,y) and ut(0,x,y) respectively.
I believe this code works for finding the function values for u however when I try to plot the results as follows:
for i=1:Nt
figure
clf
hold on
surf(X,Y,u(i,:,:))
end
I get an error saying Z must be a matrix... In my opinion this seems strange, slicing a 3d array results in a 2d matrix.
How can I make an animation that shows u as a function of x and y?
Thanks in advance! any help is greatly appreciated
P.S. I am new to this page so if I am neglecting certain guidelines when it comes to sharing code please let me know and I will adjust it.
Another way to remove the singleton dimension of your u array would be to use squeeze() as it doesn't need any information on the remaining size of the array.
for i = 1:Nt
figure
clf
hold on
surf(X, Y, squeeze(u(i, :, :)))
end
To force u(i,:,:) to match the 100 by 100 dimensions of X and Y try using the reshape() function.
for i=1:Nt
figure
clf
hold on
surf(X,Y,reshape(u(i,:,:),[100 100]));
end

Loading & Plotting Multiple Files From Directory (MATLAB)

I am trying to load multiple files from a directory I created, plot them in separate figures, and then output them as .tiff files.
I believe that I have all of the code needed for plotting the loaded files and then outputting them as .tiff files, but I am unable to get the files loaded into MATLAB initially to carry out the plotting and the output.
Function used:
function x = chaos(x0, lambda, vectorLength);
x0 = 0.5;
lambda = 3.8;
vectorLength = 1500;
x = zeros(vectorLength,1);
x(1) = x0;
for k=2:vectorLength,
x(k) = lambda*x(k-1)*(1-x(k-1));
end
T = 2;
x1 = x(1:end-2*T);
x2 = x(T+1:end-T);
x3 = x(2*T+1:end);
figure('Color',[1 1 1]);
h = plot3(x1, x2, x3);
xlabel('x(t)');
ylabel('x(t+T)');
zlabel('x(t+2T)');
Code used for creating directory and file (working):
currentFolder = pwd;
mkdir('chaos');
for k = 1:30
data=chaos(k);
full_filename = fullfile(currentFolder,['\chaos\chaos' num2str(k) '.txt']);
fid = fopen(full_filename,'w' );
fprintf(fid,'%d\n',data);
fclose(fid);
end
full_filename = fullfile(currentFolder,['\chaos\chaos1.txt']);
fileID = fopen(full_filename,'r');
formatSpec = '%f';
X = fscanf(fileID,formatSpec);
plot(X);
Code used for trying to load, plot, then output files from the created directory (not working):
for k = 1:30
dir('chaos');
x = load('chaos(k).txt');
figure('Color', [1 1 1]);
plot(x);
pause(0.1);
eval(sprintf('print -dtiff chaos%d', k));
end
I am expecting to have 30 figures plotted and outputted to the screen, and then have 30 figures outputted as .tiff files. The actual output is only showing the directory in the command window, and nothing is getting plotted or outputted as .tiff files.
EDIT: here is the updated code to fix the problem with the variable k:
x = load(['chaos', num2str(k), '.txt']);
Here's an issue:
for k = 1:30
dir('chaos');
x = load('chaos(k).txt');
Variable interpolation doesn't work like that in Matlab. If you want the value held in k to go into your string, you need to use string concatenation or sprintf:
for k = 1:30
file = sprintf('chaos%d.txt', k);
x = load(file);
Looks like you're doing the right thing further down in your output code; you just need to apply it here, too.
You probably should avoid eval, too. Call it like this:
print('-dtiff', sprintf('chaos%d', k));

How to use surf to plot sphere function in matlab

I'm trying to plot sphere function below, But I'm getting wrong result
Here is the code I'm using
x1 = [-10:1:10];
x2 = [-10:1:10];
y = zeros(1,21);
for i = 1:21
y(i) = sphere([x1(i) x2(i)]);
end
Y = meshgrid(y);
surf(x1,x2,Y);
colormap hsv;
sphere.m
function [y] = sphere(x)
d = length(x);
sum = 0;
for i = 1:d
sum = sum + x(i)^2;
end
y = sum;
end
For the sake of completness your code is not working because you are only evaluating your function on the pairs (x,x) for some x \in [-10,10] so you don't cover the whole domain. It would work with this:
x1 = [-10:1:10];
x2 = [-10:1:10];
y = zeros(1,21);
for i = 1:21
for j=1:21
Y(i,j) = sphere([x1(i) x2(j)]);
end
end
surf(x1,x2,Y);
colormap hsv;
or way faster (because you should always avoid unnecessary loops for computation time reasons):
x1 = meshgrid([-10:1:10]);
x2 = x1';
Y = x1.^2+x2.^2;
surf(x1,x2,Y)
sphere(10)
It is a MatLab built in function.
Please enjoy responsibly.
If you need to see the source code use: edit sphere or help sphere when your sphere function is not on the path.

Matlab: plot is only graphing last value in vector

I need the following code to plot the range of values of C(i) against the values of x. So based on the code at the x = 1, I need C(1), at x = 2, C(2) and so on... A simple problem Im sure, please help!
clear all; clc;
n = 15
x = 1:(n-1)
T = 500;
D = T./(n-x)
for i=1:13
C(i) = D(i+1) - D(i)
end
plot(x, C(i), 'rx')
I guess what you want is this,
clear
clc
close all
n = 15;
x = 1:(n-1);
T = 500;
D = T./(n-x);
C = zeros(length(x) - 1, 1);
for i=1:13
C(i) = D(i+1) - D(i);
end
figure, plot(C, 'rx')
It is better to preallocate the C variable, so you can plot it then.
The C(i) only gave you the last number because after the for i is 13 and C(i)as you had it only gives you C in the 13th position.
Change:
plot(x, C(i), 'rx')
To:
plot(x(1:end-1), C, 'rx')
Actually, you could replace your for loop with this:
C = diff(D);
Which calculates the difference between consecutive elements.

How to plot a matlab function for different parameters using hold on command

I have a matlab function that contain some constant parameter, I want to draw that function, on say same figure, using hold on (probably) while changing the value of that constant.
This my code:
close all
clear all
clc
m = 5;
x = 1:1:10;
y = m*x + 10;
h1 = figure;
plot(x,y)
m = 10;
figure(h1);
hold on
plot(x,y,': r')
When I tried using this code, I got two lines coincident on each others; and it looks matlab just used last value for the parameter m how can I make it use different values.
I found some stuff here, but doesn't fulfill my needs.
Any suggestions?
You need to recalculate y as well:
m = 5;
x = 1:1:10;
y = m*x + 10;
h1 = figure;
plot(x,y); hold on;
m = 10;
y = m*x + 10;
figure(h1);
plot(x,y,': r')
Or create an anonymous function:
x = 1:1:10;
f = #(m) m*x + 10;
%// and then:
h1 = figure;
plot(x,f(5) ); hold on;
plot(x,f(10),': r');
Currently, you're only updating m but you also have to calculate y again. This is why it plots exactly the same y (i.e. m is still 5) function when you issue the second plot.
You might want to use a simple for loop for that, like:
m = 5;
x = 1:1:10;
figure;
hold on;
for m=1:1:10
y = m*x + 10;
plot(x,y,': r')
end
In addition to the short answer - improving the plot..
%% Data Preparations
x = 1:10;
ms = 3; % number of different slopes
%% Graph Preparations
hold on;
% Prepare the string cell array
s = cell(1, ms);
% Handle storage
h = zeros(1, ms);
% Plot graphs
for m=1:ms
y = m*x + 10;
h(m)= plot(x,y,'Color',[1/m rand() rand()]);
s{m} = sprintf('Plot of y(m=%d)', m);
end
% Plot all or select the plots to include in the legend
ind = [ms:-1:1] .* ones(1,ms); % plot all
%ind = [ 1 3 4 ]; % plot selected
% Create legend for the selected plots
legend(h(ind), s{ind});
Additional advice: When working with MATLAB and you try to improve the performance of your code, you shoud try to avoid using for-loops since MATLAB is MATrix manipulation and that's what it can do best. Ones you've taken this philosophy in, you'll create the most beautiful code one-liners! ;)
This script is an adoption of Steve Lord's post.