I would like to plot a sawtooth function in Octave. I know that I can use the command "sawtooth(t)" but I don't have the package so I created the following function.
function x = pieceWise2bis(t)
x = zeros (size (t));
ind1 = t >= 10 & t < 13;
x(ind1) = +20;
ind2=t >= 13 & t < 16;
x(ind2) = -20;
ind3=t >= 16 & t < 19;
x(ind3) = +20;
ind4=t >= 19 & t < 22;
x(ind4) = -20;
endfunction
When I plot this function I don't get the result I'm looking for because I want a real sawtooth function and not a periodic function with crenels like that.
COuld someone tell me how I could adapt my code ?
Thank you
It appears that the usual way to load sawtooth, by installing signal which requires control.... is not working, in any case you are way better off writing this yourself. Here's one of many ways to do it:
clear; %% this line tells octave the remainder is more than just a func.
## usage: ST = sawtooth (time)
function ST = sawtooth (time)
ST=rem(time,2*pi)/2/pi;
endfunction
time=linspace(0,20,101); % second line of main program (clear is 1st)
PriSawtooth=sawtooth(time);
plot(time,PriSawtooth,'linewidth',1)
Related
Code:
function result = assess_polynomial_n(y,n)
[coeff, t, pred_accum] = fit_data(y, n);
[avg, std_dev] = compute_error(coeff,y);
[coeff1, t, pred_accum1] = fit_data(y, n+1);
[avg1, std_dev1] = compute_error(coeff1,y);
if avg1>avg
result = n;
elseif avg<0.1 && std_dev<0.1
result = n;
elseif pred_accum1.*(1)<0.0001
result = n;
else
result = 0;
end
end
***Error***
error: compute_error: operator -: nonconformant arguments (op1 is 1x12, op2 is 1x3)
error: called from
compute_error at line 11 column 17
assess_polynomial_n at line 19 column 18
__tester__.octave at line 38 column 1
Does anyone know why I could be getting this error? We're supposed to be working in MATLAB but pasting our code into Moodle which uses Octave if that clears anything up.
I also will post the functions I'm calling for reference since the error is occurring in Compute_Error. This is a part of an overall project where I was to define the functions I'm calling before creating assess_polynomial_n.
function [coeff, t, pred_accum] = fit_data(y, n)
len = length(y);
t = 10*[0:len-1];
coeff = polyfit(t, y, n);
pred_accum = polyval(coeff, t);
end
function [avg std_dev] = compute_error(x,y)
s=[];
for i=1:length(x)
error=abs(x(i)-y(i));
s=[s,error];
end
avg = mean(s);
std_dev = std(s);
end
The problem lies in this line of code:
[avg1, std_dev1] = compute_error(coeff1,y);
You are trying to compute the error between the original data and the coefficients of the fitted polynomial. It doesn't make sense, right?
Instead, you should compute the error between the original data and the fitted data, which is the polynomial's output at each t value. The correct code would be:
[avg1, std_dev1] = compute_error(pred_accum1,y);
I have a problen in scilab
How can I plot functions containing if and < like
function y = alpha(t)
if (t < 227.8) then
y = 0.75;
elseif (t < 300) then
y = 2.8 - 0.009 .* t;
else
y = 0.1;
end
endfunction
and
function [r]=minus_alpha(t)
r = 1 - alpha(t)
endfunction
When I use
x = linspace(0,300)
plot(x, alpha(x))
I got the error message
WARNING: Transposing row vector X to get compatible dimensions
plot2d: falsche Größe für Eingangsargument: inkompatible Größen.
Error 999 : in plot2d called by plot
Sorry for german mix. Thank you.
You can avoid explicit loop and be more efficient using the followin code
function y = alpha(t)
y=0.1*ones(t);
y(t<227.8)=0.75;
i=t>=227.8&t<300;
y(i)=2.8 - 0.009 .* t(i);
endfunction
It is really sad to see a great majority of Scilab community is not aware of vectorized operations. You can change your function to:
function y = alpha(t)
y = 0.1;
if t < 227.8 then
y = 0.75;
elseif t < 300 then
y = 2.8 - 0.009 * t;
end
y = 1 - y;
endfunction
and then use feval to broadcast the function over the sequence:
x = linspace(0, 300);
plot2d(x, feval(x, alpha));
which results:
rule of thumb if you are using for loop you need to revise your code and if someone is offering you a code where there is unnecessary for loop you shouldn't probably use it.
All the proposed answers are overcomplicated considering that the function alpha in the original demand is piecewise-affine. In Scilab in can be coded that way:
x = linspace(0,400,1000);
plot(x,linear_interpn(x,[227.8 300],[0.75 0.1]))
i.e. you just have to know the nodes coordinates (here abscissae) and value of the function at nodes. The function linear_interpn does also multilinear interpolation, it is worth knowing it guys...
If you check the output of your alpha(x), you will see that it is just a scalar (not a vector). I guess you wanted something like this, so it's necessary to iterate through t to compute each value of y based on the value of t:
clc;
clear;
function y = alpha(t)
for i=1:size(t,"*")
if t(i) < 227.8 then
y(i) = 0.75;
elseif t(i) < 300 then
y(i) = 2.8 - 0.009 * t(i);
else
y(i) = 0.1;
end
end
endfunction
x = linspace(0,300);
plot2d(x,alpha(x));
If you find the answer useful, please do not forget to accept it, so others will see that your problem is solved.
Before your answers (thank you) my workaround was a combination of indicator functions composed with floor and exp( -t^2):
function y = alpha(t)
y = floor(exp(-(t .* (t-T1)) / (T1*T1))) * 0.75
+ floor(exp(-((t-T2) .* (t- T1) / (2000)))) .* (2.8-0.009 .* t)
+ floor(exp(-((t-T2) .* (t-1000) / (200000))))*0.1
endfunction
I am new to Octave although I can say I am an expert Matlab user. I am running Octave on a Linux server (Red Hat) remotely through PuTTY, from a windows machine.
I am observing a very strange behavior in Octave. I call myfun(a) which performs as expected giving the sought results. Now, if I run, say, myfun(b) with b!=a, I get again myfun(a). Clear -f does not solve the problem. I need to reboot octave to change the parameters.
What am I doing wrong?
Thanks a lot
Francesco
This is the code for the function I mentioned:
function [a, v, obj, infos, iter] = mle_garch( p )
#{
% this function estimates the GARCH(1,1) parameters
% it is assumed we pass the adjusted price level p
#}
global y = (diff(log(p))-mean(diff(log(p))))*100;
global h = zeros(size(y));
a0 = [var(y)*0.9; 0.8; 0.1];
[a, obj, infos, iter] = sqp(a0, #loglike_garch, [], #loglike_con, [], [], 1000);
v = sqrt(h * 260);
endfunction
function g = loglike_garch( a )
global y h
n = length(y);
h(1) = var(y);
for i = 2 : n,
h(i) = a(1) + a(2) * h(i-1) + a(3) * y(i-1)^2;
endfor
g = 0.5 * ( sum(log(h)) + sum(y.^2./h) ) / n;
endfunction
function f = loglike_con( a )
f = [1;0;0;0] + [0 -1 -1;eye(3)] * a;
endfunction
I'm assuming the myfun you mentioned is mle_garch. The problem is the way you're initializing the global h and v variables (do you really need them to be global?). When you have a piece of code like this
global y = (diff(log(p))-mean(diff(log(p))))*100;
global h = zeros(size(y));
the values of y and h are defined the first time only. You can change their values later on, but this specific lines will never be ran again. Since your code only uses the input argument to define these two variables, the value which you use to run the function the first time will be used every single other time. If you really want to keep those variables global, replace it with the following:
global y;
global h;
y = (diff(log(p))-mean(diff(log(p))))*100;
h = zeros(size(y));
But I don't see any reason to keep them global so just don't make them global.
Also, you mentioned this code worked fine in Matlab. I was under the impression that you couldn't initialize global and persistent variables in Matlab which would make your code illegal in Matlab.
I have followed the tutorial on http://www.mit.edu/people/abbe/matlab/ode.html and prepared a function as follows:
function dxy = diffxy(xy)
%
%split xy into variables in our equations
%
x = xy(1);
xdot = xy(2);
y = xy(3);
%
% define the derivatives of these variables from equations
%
xdot = xdot;
ydot = 3*x + 2*y + 5;
xdoubledot = 3 - ydot + 2*xdot;
%
%return the derivatives in dxy in the right order
%
dxy = [xdot; xdoubledot; ydot]
end
When I call it using
[T, XY] = ode45('diffxy',0,10,[0 1 0])
I get an error
??? Error using ==> diffxy
Too many input arguments.
I also tried
XY= ode45(#diffxy,[0 10],[0;1;0])
Anybody have any idea?
haven't read the whole tutorial but aren't you supposed to define your function as
function dxy = diffxy(t, xy)
where t is time vector
I am a new user of MATLAB. I want to find the value that makes f(x) = 0, using the Newton-Raphson method. I have tried to write a code, but it seems that it's difficult to implement Newton-Raphson method. This is what I have so far:
function x = newton(x0, tolerance)
tolerance = 1.e-10;
format short e;
Params = load('saved_data.mat');
theta = pi/2;
zeta = cos(theta);
I = eye(Params.n,Params.n);
Q = zeta*I-Params.p*Params.p';
% T is a matrix(5,5)
Mroot = Params.M.^(1/2); %optimization
T = Mroot*Q*Mroot;
% Find the eigenvalues
E = real(eig(T));
% Find the negative eigenvalues
% Find the smallest negative eigenvalue
gamma = min(E);
% Now solve for lambda
M_inv = inv(Params.M); %optimization
zm = Params.zm;
x = x0;
err = (x - xPrev)/x;
while abs(err) > tolerance
xPrev = x;
x = xPrev - f(xPrev)./dfdx(xPrev);
% stop criterion: (f(x) - 0) < tolerance
err = f(x);
end
% stop criterion: change of x < tolerance % err = x - xPrev;
end
The above function is used like so:
% Calculate the functions
Winv = inv(M_inv+x.*Q);
f = #(x)( zm'*M_inv*Winv*M_inv*zm);
dfdx = #(x)(-zm'*M_inv*Winv*Q*M_inv*zm);
x0 = (-1/gamma)/2;
xRoot = newton(x0,1e-10);
The question isn't particularly clear. However, do you need to implement the root finding yourself? If not then just use Matlab's built in function fzero (not based on Newton-Raphson).
If you do need your own implementation of the Newton-Raphson method then I suggest using one of the answers to Newton Raphsons method in Matlab? as your starting point.
Edit: The following isn't answering your question, but is just a note on coding style.
It is useful to split your program up into reusable chunks. In this case your root finding should be separated from your function construction. I recommend writing your Newton-Raphson method in a separate file and call this from the script where you define your function and its derivative. Your source would then look some thing like:
% Define the function (and its derivative) to perform root finding on:
Params = load('saved_data.mat');
theta = pi/2;
zeta = cos(theta);
I = eye(Params.n,Params.n);
Q = zeta*I-Params.p*Params.p';
Mroot = Params.M.^(1/2);
T = Mroot*Q*Mroot; %T is a matrix(5,5)
E = real(eig(T)); % Find the eigen-values
gamma = min(E); % Find the smallest negative eigen value
% Now solve for lambda (what is lambda?)
M_inv = inv(Params.M);
zm = Params.zm;
Winv = inv(M_inv+x.*Q);
f = #(x)( zm'*M_inv*Winv*M_inv*zm);
dfdx = #(x)(-zm'*M_inv*Winv*Q*M_inv*zm);
x0 = (-1./gamma)/2.;
xRoot = newton(f, dfdx, x0, 1e-10);
In newton.m you would have your implementation of the Newton-Raphson method, which takes as arguments the function handles you define (f and dfdx). Using your code given in the question, this would look something like
function root = newton(f, df, x0, tol)
root = x0; % Initial guess for the root
MAXIT = 20; % Maximum number of iterations
for j = 1:MAXIT;
dx = f(root) / df(root);
root = root - dx
% Stop criterion:
if abs(dx) < tolerance
return
end
end
% Raise error if maximum number of iterations reached.
error('newton: maximum number of allowed iterations exceeded.')
end
Notice that I avoided using an infinite loop.