forgive me if the answer is this is terribly obvious or if there's a much better way to do this.
I'm trying to make a function that accepts a function of x (e.g. x^2 + 5x + 2), and use that input to create a function handle. That way I can use that function for whatever else I need it to do.
I think the problem is just that I don't know what all the different function types are, and I don't understand how to "concatenate" the "#(x)" and the input function correctly to make the function handle.
Here's what I tried:
function test(input1)
function_1 = #(x) + input1
end
It says that input1 is of type double, even if it's just a letter.
And if I try to enter the input as a string and convert it to symbolic data, I just get an array of numbers for the concatentaion.
Any help would be greatly appreciated, thanks.
Passing a string probably won't get you what you want, or it will get ugly.
This might be off topic, but it's important to understand that anonymous functions store the value of non-input variables at the time of creation. Any values that you want to change on each call to the function need to be input arguments.
>> a = pi;
>> fun = #(x) x * a;
>> fun(2)
ans =
6.2832
You can see the stored values as follows,
>> fi = functions(fun)
fi =
function: '#(x)x*a'
type: 'anonymous'
file: ''
workspace: {[1x1 struct]}
>> fi.workspace{1}
ans =
a: 3.1416
If your intention is to have another input argument, just have two input arguments:
>> fun = #(x,y) x * y;
>> fun(2,pi)
ans =
6.2832
However, you can pass a function handle to a function, and then call it. Perhaps this is what you're after:
function myfun = funTester(fh,x)
% presumably do something useful here
myfun = fh(x);
end
For example,
>> fun = #(x) x.^2 + 5*x + 2
fun =
#(x)x.^2+5*x+2
>> funTester(fun,-2)
ans =
-4
Final thought: Construct a handle with eval:
>> expression = 'x^2 + 5*x + 2';
>> eval(['h = #(x) ' expression]) % put this in your function
h =
#(x)x^2+5*x+2
Or str2func, (thanks Luis Mendo)
h = str2func(['#(x)' expression])
Either way it's not too pretty, hence my suggestion to just pass a handle.
Related
Hi I am new to matlab so not familiar with its grammar.
I want to write a function to solve some functions using specific algo.
What I want to do is to write a function using another function which I want to slove as input.
For example, if I want to get the root of x^2 - 1 = 0 ,I need to plug in this function as in input.
my code is like
function [y] = brent(f, x0, x1, max_iter, tolerance)
fx0 = f(x0)
fx1 = f(x1)
......
end
f is the function I want to solve. My question is how should I write the code so the function 'brent' can use the function 'f' to calculate the values at specific points.
ex. In the second line, I need to get the value of f(x0) (x0 is a point).
Matlab talks about function handles. Those can be input parameter as anything:
Write your main function:
function a = func(f,x)
a = f(x) + 7;
Define your function to be input, and call 'normally'
>> myfun = #(x) x^2-1;
>> func(myfun,3)
ans =
15
>> func(#sin,0)
ans =
7
see:
https://se.mathworks.com/help/matlab/matlab_prog/creating-a-function-handle.html
I'm trying to write a simple script that request a equation as input and I like to calculate with this function more than once without always requesting user input.
My current script defined f as function handle and executed the function 2 times, so I'm always asking for a new equation, which is not desirable.
f = #(x) input('f(x) = ');
a = f(2); % requests user input
b = f(3); % requests user input again
And it should look more like this (not working).
func = input('f(x) = ');
f = #(x) func;
a = f(2);
b = f(3);
And here without user input to get an idea what I try to achieve.
f = #(x) x^2;
a = f(2);
b = f(3);
I think I found a solution with Symbolic Math Toolbox, but I do not have this addon, so I cannot use/test it.
Is there another solution?
There's no need for the Symbolic Mathematics Toolbox here. You can still use input. Bear in mind that the default method of input is to directly take the input and assign it as a variable where the input is assumed to be syntactically correct according to MATLAB rules. That's not what you want. You'll want to take the input as a string by using the 's' option as the second parameter then use str2func to convert the string into an anonymous function:
func = input('f(x) = ', 's');
f = str2func(['#(x) ' func]);
a = f(2);
b = f(3);
Take note that I had to concatenate the #(x) anonymous function string with the inputted function you provided with input.
Example Run
Let's say I want to create a function that squares every element in the input:
>> func = input('f(x) = ', 's');
f(x) = x.^2
>> f = str2func(['#(x) ' func])
f =
#(x)x.^2
>> a = f(2)
a =
4
>> b = f(3)
b =
9
Take special note that I assumed the function will element-wise square each elements in the input. The . operator in front of the exponentiation operator (i.e. ^) is very important.
When I type help gmres in MATLAB I get the following example:
n = 21; A = gallery('wilk',n); b = sum(A,2);
tol = 1e-12; maxit = 15;
x1 = gmres(#(x)afun(x,n),b,10,tol,maxit,#(x)mfun(x,n));
where the two functions are:
function y = afun(x,n)
y = [0; x(1:n-1)] + [((n-1)/2:-1:0)'; (1:(n-1)/2)'].*x+[x(2:n); 0];
end
and
function y = mfun(r,n)
y = r ./ [((n-1)/2:-1:1)'; 1; (1:(n-1)/2)'];
end
I tested it and it works great. My question is in both those functions what is the value for x since we never give it one?
Also shouldn't the call to gmres be written like this: (y in the #handle)
x1 = gmres(#(y)afun(x,n),b,10,tol,maxit,#(y)mfun(x,n));
Function handles are one way to parametrize functions in MATLAB. From the documentation page, we find the following example:
b = 2;
c = 3.5;
cubicpoly = #(x) x^3 + b*x + c;
x = fzero(cubicpoly,0)
which results in:
x =
-1.0945
So what's happening here? fzero is a so-called function function, that takes function handles as inputs, and performs operations on them -- in this case, finds the root of the given function. Practically, this means that fzero decides which values for the input argument x to cubicpoly to try in order to find the root. This means the user just provides a function - no need to give the inputs - and fzero will query the function with different values for x to eventually find the root.
The function you ask about, gmres, operates in a similar manner. What this means is that you merely need to provide a function that takes an appropriate number of input arguments, and gmres will take care of calling it with appropriate inputs to produce its output.
Finally, let's consider your suggestion of calling gmres as follows:
x1 = gmres(#(y)afun(x,n),b,10,tol,maxit,#(y)mfun(x,n));
This might work, or then again it might not -- it depends whether you have a variable called x in the workspace of the function eventually calling either afun or mfun. Notice that now the function handles take one input, y, but its value is nowhere used in the expression of the function defined. This means it will not have any effect on the output.
Consider the following example to illustrate what happens:
f = #(y)2*x+1; % define a function handle
f(1) % error! Undefined function or variable 'x'!
% the following this works, and g will now use x from the workspace
x = 42;
g = #(y)2*x+1; % define a function handle that knows about x
g(1)
g(2)
g(3) % ...but the result will be independent of y as it's not used.
I am looking to use the fminsearch function for minimization. According to the documentation, fminsearch requires a function handle and initial parameter estimate.
However, I have been struggling to create a function handle that accepts a variable number of inputs. This is an example of how I would like my code to behave:
for i = 1:M
fhandle = #(x)(x(i) + #fhandle)
end
In this example, the final fhandle is the sum of all x. Is there any way to implement this and optimize all x values such that fhandle is minimized?
Function handles accept varargin. So your exemple can be rewriten to accept a variable number of inputs:
fhandle = #(varargin) sum([varargin{:}])
and then
>> fhandle(1)
ans =
1
>> fhandle(1,2)
ans =
3
>> fhandle(1,2,3)
ans =
6
Best,
You can do in matlab something like this:
>> fh = #(x) x^2
fh =
#(x)x^2
and then
>> fh(3)
ans =
9
Now I look for a way to create the anonymous function and call it in one line, like this (it does not work):
#(x) x^2 (3) <-- This code does not work!
Is there a way to do it?
feval( #(x) x^2, 3) is what you need.
This would work (it works also with matrixes):
arrayfun(#(x) x^2,3)