How to use derive.m function to get central differentioation of f(x) - matlab

I've a function that can calculate central difference of f(x) but I'm basic user of matlab and I can't define f(x) for function I've mentioned.
Can any body help me and define f(x) for this function?
INPUTS are a function f; a value
of h; a specific point a; the number of rows n. The input function f(x)
should be defined as an M-file.
My f(x) is : S(x) = 10*x-sin(x) with steps: 0.1
I want to get df(x) near the piont=pi/6
I wrote:
clc
syms x
derive(10*x-sin(x),0.1,pi/6,14)
but I've got this error :
Error using feval
Argument must contain a string or function_handle.
Error in derive (line 7)
D(1,1)=(feval(f,a+h)-feval(f,a-h))/(2*h);
Error in centre(line 2)
========================================
the function derive.m is here:
function derive(f,h,a,n)
% Approximate the derivative of a function at x = a.
disp(' Derivative table')
disp('______________________________________________')
disp(' i h Di,1 Di,2 Di,3 ... ')
disp('______________________________________________')
D(1,1)=(feval(f,a+h)-feval(f,a-h))/(2*h);
fprintf('%2.0f %8.4f %12.4f\n',1,h,D(1,1));
for i=1:n-1
h=h/2;
D(i+1,1)=(feval(f,a+h)-feval(f,a-h))/(2*h);
fprintf('%2.0f %8.4f %12.4f',i+1,h,D(i+1,1));
for k=1:i
D(i+1,k+1)=D(i+1,k)+(D(i+1,k)-D(i,k))/((4^k)-1);
fprintf('%12.4f',D(i+1,k+1));
end
fprintf('\n');
end

feval expects a function handle, that is a MatLab function handle. What you provided (10*x-sin(x)) is a symbolic expression.
You can define a function handle as follows:
f(x) = 10*x-sin(x);
Now f is a MatLab function handle, and you can use it as you wish:
derive(f,0.1,pi/6,14)
EDIT
You can also use an anonymous functions
derive((x)(10*x-sin(x)),0.1,pi/6,14)
END EDIT
Note, you do not need syms x, it defines x as a symbol, but in your function definition you use the parameter x defined in f(x).
EDIT
If you want to use a symbolic function, you can convert it to a MatLab function handle using matlabFunction

Related

put argument inside mathematical function in matlab [duplicate]

I want to write a function that returns the value of f(y) for any value of y:
f(y) =tan( sin(y) - sin(tan(y)) )
How can I write this as a function in MATLAB?
Here is an example function for your purpose
function y = f(x)
y = tan(sin(x)-sin(tan(x)));
end
You could use an anonymous function, as elluded to in the comments by
obchardon:
f = #(y) tan(sin(y) - sin(tan(y)))
% usage like any other function:
f(1)
Note that you do not include the (y) on the left hand side of the =, this syntax is reserved for indexing into variables, or symbolic math.

MATLAB Unable to Store Symbolic Function with Multiple Variables

I'm trying to take the definite integral from -1 to 1 of a function with respect to x. The function has variables a, b, c, d, and x, all of which I've defined as syms variables. I'm trying to keep a, b, c, d in my final integral because I'll later be differentiating with respect to each one for an optimization problem. Here's the current code that I have:
syms f(x);
syms a b c d;
f(x)= (exp(x)-a*(1/sqrt(2))-b*(sqrt(3/2)*x)-c((sqrt(45/8))*(x^2-(1/3)))+d((sqrt(175/8))*((x^3)-(3/5)*(x))))^2;
integral = int(f, x, [-1 1]);
disp(integral);
Similar code worked when I tried it using only variables x and y for a smaller function. However, when I try this code, I get:
Error using sym/subsindex (line 825) Invalid indexing or function
definition. Indexing must follow MATLAB indexing. Function arguments
must be symbolic variables, and function body must be sym expression.
Error in sym/subsref (line 870)
R_tilde = builtin('subsref',L_tilde,Idx);
Error in HW11 (line 4)
f(x)= (exp(x)-a*(1/sqrt(2))-b*(sqrt(3/2)x)-c((sqrt(45/8))(x^2-(1/3)))+d((sqrt(175/8))((x^3)-(3/5)(x))))^2;
I'm pretty new to symbolic functions and syms variables in MATLAB, why is MATLAB rejecting this code? The similar code that I tried that worked was:
syms f(x);
syms y;
f(x) = (x^2) + y;
integral = int(f, x, [0 3]);
disp(integral);
As mentioned in the comment by Adam, you probably forgot to add a multiplication operator * after the the c and d, so when you write c(...) and d(...) MATLAB treats these as indexing of an array but you cannot index arrays with symbolic variables or expressions. You need to change it to c*(...) and d*(...).
Replace:
f(x)= (exp(x)-a*(1/sqrt(2))-b*(sqrt(3/2)*x)-c((sqrt(45/8))*(x^2-(1/3)))+d((sqrt(175/8))*((x^3)-(3/5)*(x))))^2;
With:
f(x)= (exp(x)-a*(1/sqrt(2))-b*(sqrt(3/2)*x)-c*((sqrt(45/8))*(x^2-(1/3)))+d*((sqrt(175/8))*((x^3)-(3/5)*(x))))^2;

How to use fzero() to solve polynomial equation in MATLAB?

I would like to solve the following polynomial numerically for r:
I am trying to use fzero() as follows:
r = (5/(r^2*9))- ((2)/(9*(6-r)^2))
x0 = 10; % some initial point
x = fzero(r,x0)
How can this be done with fzero()?
Input variable and function name should be different
Just change the function name to pol
To use fzero the function pol have to be a function handle
defined via #
pol =#(r) (5/(r^2*9))- ((2)/(9*(6-r)^2))
x0 = 10; % some initial point
x = fzero(pol,x0)
solution
x = 3.6754
It should be noted that, the first argument in fzero() should be "a function handle, inline function, or string containing the name of the function to evaluate", but yours is just an expression, which is not valid.
Besides the approach by #Adam (using function handle), another way is to use anonymous function, i.e.,
x = fzero(#(r) (5/(r^2*9))- ((2)/(9*(6-r)^2)) ,x0)
where
#(r) (5/(r^2*9))- ((2)/(9*(6-r)^2))
is the anonymous function with respect to argument r.
You will get the same result that x = 3.6754.

ODE solver producing runtime error - not enough input arguments [duplicate]

I have a use case as follows:
Inside F.m I have a function F that takes as its argument a 2 x 1 matrix x. F needs to matrix multiply the matrix kmat by x. kmat is a variable that is generated by a script.
So, what I did was set kmat to be global in the script:
global kmat;
kmat = rand(2);
In F.m:
function result = F(x)
global kmat;
result = kmat*x;
end
Then finally, in the script I have (x_0 has already been defined as an appropriate 2 x 1 matrix, and tstart and tend are positive integers):
xs = ode45(F, [tstart, tend], x_0);
However, this is causing the error:
Error using F (line 3)
Not enough input arguments.
Error in script (line 12)
xs = ode45(F, [tstart, tend], x_0);
What is going on here, and what can I do to fix it? Alternatively, what is the right way to pass kmat to F?
Firstly, the proper way to handle kmat is to make it an input argument to F.m
function result = F(x,kmat)
result = kmat*x;
end
Secondly, the input function to ode45 must be a function with inputs t and x (possibly vectors, t is the dependent variable and x is the dependent). Since your F function doesn't have t as an input argument, and you have an extra parameter kmat, you have to make a small anonymous function when you call ode45
ode45(#(t,x) F(x,kmat),[tstart tend],x_0)
If your derivative function was function result=derivative(t,x), then you simply do ode45(#derivative,[tstart tend],x_0) as Erik said.
I believe F in ode45(F,...) should be a function handle, i.e. #F. Also, you can have a look at this page of the MATLAB documentation for different methods to pass extra parameters to functions.

matlab ode45 how to change a parameter inside the function continiously

i am trying to solve a differential equation using ode45, I have a function in which one of the parameters has to vary by specific step, here is my function:
function f=RSJ(y,t,M1,P,M2,E,current)
f=(current/P)-(M1/P)*sin(y)+(M2/P)*sin(y+E);
P, M1, M2 & E are numerical constants, current is the parameter which I should resolve this differential equation for several cases, for example current=0:1:10
how can I do such a thing?
Use a closure (a.k.a. anonymous or lambda function):
% declare t, y, tspan and y0
% [...]
current = 6e-7 : 1e-8 : 8.5e-7;
for k=1:length(current)
f = #(y, t, M1, P, M2, E) (current(k)/P)-(M1/P)*sin(y)+(M2/P)*sin(y+E);
[t{k}, y{k}] = ode45(f, tspan, y0);
end
A quick and dirty solution. Define current as a global variable (you need to do this in both the base workspace and in the function) and use a for loop, e.g.
current_vector=1e-7*(6:0.1:8.5);
global current
for k=1:length(current_vector)
current = current_vector(k);
[t{k},y{k}]=ode45(f,<tspan>,<y0>)
end
Replace <tspan> and <y0> by the appropriate values/variables. I assume the other constants are defined in the body of the function, in which case your function should look something like this:
function f=RSJ(t,y)
global current
M1 = ... % etc...
f=(current/P)-(M1/P)*sin(y)+(M2/P)*sin(y+E);
end
BTW, I don't see any explicit dependence on time t in your function...