Anonymous functions in cftool GUI

4 次查看(过去 30 天)
Does anyone know if it is possible to use anonymous functions in the custom equation box of the cftool GUI?
Simply typing them in results in an error in R2012a, e.g.
@(x,tau) exp(-t/tau)
Expression @(x,tau) exp(-t/tau) is not a valid MATLAB expression, has non-scalar coefficients, or cannot be evaluated:
Undefined function 'imag' for input arguments of type 'function_handle'.
My motivation is to use anonymous functions as arguments of a custom fitting function to be called by cftool, e.g.:
MyCustomFitFunction(x,hFun1,hFun2,FitParam1,FitParam2)
with hFun1 and hFun2 as function handles.
I imagine this is very possible using the non-interactive fitting tools, but was keen on using the GUI.
Thanks

采纳的回答

Joe V
Joe V 2014-8-20
Hi Marcelo, sorry I didn't see your comment until just now. I no longer have access to the curve fitting toolbox to test, but I think this is what you want to type into the custom equation box:
MyConvolutionFunction(x, @(x)exp(-x/a), @(x)exp(-(x-b).^2)./(2*(c.^2))))
Here's how that works: Whenever cftool wants to evaluate your analytic function, it evaluates the above expression. In doing so, it creates two anonymous function handles, and then passes them (along with x) into MyConvolutionFunction. The anonymous function handles are created with only x as an argument, so the values of a, b, and c are drawn from the workspace at the time the function handles are created (i.e. when cftool is evaluating the expression). I believe this should work. One note: I am guessing that cftool uses inline to parse the expression in the custom equation box. In my own testing, I noticed that inline isn't smart enough to identify the parameters of anonymous functions. This means it's important that you make the anonymous function argument @(x). If you use some other variable like @(t), then inline will erroneously think that t is another parameter in your expression that cftool needs to provide, and that will cause problems for cftool.
One more comment: Function handles in MATLAB incur a slight performance penalty over typing in expressions directly, so if you find cftool is unacceptably slow you can try the "hard-coded" approach.
Hope this helps!

更多回答(2 个)

Joe V
Joe V 2013-9-28
You don't need to use an anonymous function. Just type in your function, making sure to use x as the independent variable:
exp(-x/tau)
The Curve Fitting Tool will recognize x as the independent variable and tau as a parameter of the fit. (If the curve you want to fit to is literally exp(-x/tau), you might not need a custom equation -- the Exponential fit type will fit to the curve a*exp(b*x).)
  1 个评论
Marcelo Alcocer
Marcelo Alcocer 2013-9-28
Thanks for the reply, but this is not quite what I was looking for. Let me explain my problem in more depth.
The experimental data I wish to fit can be modelled as the convolution of two (often analytical) 1-D functions. I have written a Matlab function which returns the result of the convolution, correctly scaled and ready for comparison with my experimental data.
In order to keep things as general as possible, I have used function handles to define the two input functions to be convolved. Therefore, my convolution function looks something like:
function output = MyConvolutionFunction(x, hFun1, hFun2)
output = conv(hFun1(x),hFun2(x)); % Convolve analytical functions
% ...further code here to scale output, etc.
end
where hFun1 and hFun2 are function handles to the analytical functions to be convolved.
I would now like to use this function as a custom equation in cftool. However as mentioned previously, inputting MyConvolutionFunction(x,hFun1,hFun2) in the custom equation box with hFun1 and hFun2 as anonymous functions generates an error due to the function handle arguments.
It's clear that the function handles are causing this problem from the last line of error message ("Undefined function 'imag' for input arguments of type 'function_handle'"). Also, if I encapsulate my function in another function to remove the function handle arguments, cftool does not throw an error, e.g.:
function output = MyExpGaussConvFunc(x)
hFun1 = @(t) exp(-t);
hFun2 = @(t) exp(-(t.^2)/(2*(1.^2)));
output = MyConvolutionFunction(x,hFun1,hFun2);
end
This of course reduces the flexibility of my code as a new encapsulating function must be written for each combination of analytical functions to be convolved.
So again, does anyone know if it is at all possible to use anonymous functions in the custom equation box of the cftool GUI?

请先登录,再进行评论。


Marcelo Alcocer
Marcelo Alcocer 2014-9-2
Using anonymous functions with x as the only argument works a treat.
I can confirm that whatever cftool uses to parse the custom equation box does not pick up anonymous function arguments, so @(x,a) , @(x,a,b) , etc. do not work. From what I can tell however, undeclared arguments do not seem to be drawn from the workspace, but are instead treated as fit parameters and so can be controlled as normal from within cftool .
As you rightly pointed out, this implies that the only anonymous function argument allowed is the independent variable (usually x ). Given that this is not really passed as an argument, but rather as the original variable I guess the logical thing to do would be to omit it entirely, e.g.
MyConvolutionFunction(x, @()exp(-x/a), @()exp(-(x-b).^2)./(2*(c.^2))))
Unfortunately, it looks like inline also struggles with this and throws an error related to too many input arguments.
As an aside, the R2014a documentation warns that inline will be removed in future releases, so I guess cftool's behaviour may change in future.
All very impressive considering you don't have the toolbox! Thanks!

类别

Help CenterFile Exchange 中查找有关 Get Started with Curve Fitting Toolbox 的更多信息

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by