Function handle in varargin not recognized

5 次查看(过去 30 天)
When i am trying to input a function manually the scripts doesent recognize x ( Unrecognized function or variable 'x'. ) see pictures
How am i using the function handle wrong?
Thanks
function drawfunction(varargin)
switch nargin
case 0
disp('0 inparam. chosen')
f = @(x) exp(atan(x)+sin(x))+log(2+x.^4)-(cos(3*x)/(1+x.^2));
x = linspace(-3,8);
color = 'r:';
case 1
disp('1 inparam. chosen')
f = @(x) varargin(1);
x = linspace(-3,8);
color = 'r:';
case 2
disp('2 inparam. chosen')
f = @(x) varargin(1);
x = varargin(2);
color = 'r:';
case 3
disp('3 inparam. chosen')
f = @(x)varargin(1);
x = varargin(2);
color = varargin(3);
otherwise
error('Unexpexted inputs')
end
plot(f(x),color)
No input:
One input: (same function)

回答(1 个)

Voss
Voss 2022-6-16
You're calling drawfunction with an expression that MATLAB tries to evaluate before sending the result of that evaluation in to drawfunction.
What you mean to do is to send a function handle to drawfunction, so call it like this:
drawfunction( @(x)exp(atan(x)+sin(x)) ) % ( etc., long expression )
Then, inside drawfunction, varargin{1} (note the curly braces, by the way) is that function handle you passed in, so there's no need to do this:
f = @(x)varargin(1) % neither one of these is correct
f = @(x)varargin{1}
It's just this:
f = varargin{1}; % varargin{1}, i.e., the first input argument, is already a function handle
  3 个评论
Mikael Freyhult
Mikael Freyhult 2022-6-16
Thank you very much!
I understand I will need to "create the function handle" when calling the function, or as you described use srting2func. I was a bit confused as why it didn't just pass the argument to varagin{1} but then i understand that it evaluates it "before" sending it into the function.
Sorry if my terminology is under par :P
If i may ask a subsequent question, is there any way to, without changing the code to enter a blank argument as varagin{1} and varagin{2} then inputing varagin{3}?
I didn't manage it by leaving blanks as -> drawfunction( , ,'b:')
to only change the plot, see image
i tried increasing number of cases to include only for example varagin{3} but it did not work
%%% Code below
function drawfunction(varargin)
switch nargin
case 0
disp('0 inparam. chosen')
f = @(x) exp(atan(x)+sin(x))+log(2+x.^4)-(cos(3*x)/(1+x.^2));
x = linspace(-3,8);
color = 'r:';
case 1
disp('first inparam. chosen')
f = varargin{1};
x = linspace(-3,8);
color = 'r:';
case 2
disp('1,2 inparam. chosen')
f = varargin{1};
x = varargin{2};
color = 'r:';
case 3
disp('1,2,3 inparam. chosen')
f = varargin{1};
x = varargin{2};
color = varargin{3};
case 4
disp('Third inparam. chosen')
f = @(x) exp(atan(x)+sin(x))+log(2+x.^4)-(cos(3*x)/(1+x.^2));
x = linspace(-3,8);
color = varargin{3};
case 5
disp('2,3 inparam. chosen')
f = @(x) exp(atan(x)+sin(x))+log(2+x.^4)-(cos(3*x)/(1+x.^2));
x = varargin{2};
color = varargin{3};
case 6
disp('1,3 inparam. chosen')
f = varargin{1};
x = linspace(-3,8);
color = varargin{3};
otherwise
error('Unexpexted inputs')
end
plot(f(x),color)
Voss
Voss 2022-6-16
编辑:Voss 2022-6-16
As you've discovered, you cannot send missing arguments like that
drawfunction( , , 'b:')
If you want to use an input argument, then all previous input arguments must also be specified.
However, you can write your function such that it handles certain values specially. For instance, you might use the empty array [] as a special value that indicates to the function that the default value for that argument should be used (this is only useful if [] is not a valid value for that argument).
If you do that, then you could call drawfunction like this:
drawfunction([], [], 'b:')
3 inparam. chosen
to get the default function and x values. Of course, you also have to set up drawfunction to handle [] appropriately, which is easy if you use the argument handling structure I showed in my last comment:
function drawfunction(varargin)
if nargin >= 1 && ~isempty(varargin{1}) % at least one argument given and it's not empty
if ischar(varargin{1})
f = str2func(['@(x)' varargin{1}]);
else
f = varargin{1};
end
else
f = @(x)exp(atan(x)+sin(x)); % default function
end
if nargin >= 2 && ~isempty(varargin{2}) % at least two arguments given and argument 2 is not empty
x = varargin{2};
else
x = linspace(-3,8); % default x
end
if nargin >= 3 && ~isempty(varargin{3}) % at least three arguments given and argument 3 is not empty
color = varargin{3};
else
color = 'r:'; % default color/line-spec
end
if nargin >= 4
% error('Unexpexted inputs');
warning('drawfunction: Extra arguments ignored.');
else
disp(sprintf('%d inparam. chosen',nargin));
end
plot(x,f(x),color);
end
(Note that I changed
plot(f(x),color);
to
plot(x,f(x),color);
because I think that makes more sense.)

请先登录,再进行评论。

类别

Help CenterFile Exchange 中查找有关 Argument Definitions 的更多信息

产品


版本

R2021b

Community Treasure Hunt

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

Start Hunting!

Translated by