This is my function
function [mean,stdev] = stat(x)
n = length(x);
mean = sum(x)/n;
stdev = sqrt(sum((x-mean).^2/n));
and I called
[mean stdev] = stat([12.7 45.4 98.9 26.6 53/1])
??? Undefined function or method 'stat' for input arguments of type 'double'.
I also tried
mean,stdev = stat([12.7 45.4 98.9 26.6 53/1])
??? Input argument "x" is undefined.
Error in ==> mean at 30
y = sum(x,dim)/size(x,dim);
Both of them are wrong and I cannot figure out why.
Could you please help me =] Thanks a lot
Your function looks fine to me, therefore I assume that your Matlab "Current Directory" is not the same directory where your function lives.
Another reason might be that the file in which this function exists does not have the same as this function. In order for Matlab to know that this function exists, it has to live in a separate file called stat.m (note how file name is the same as the function name).
Related
This is the code I write in Matlab. As you can see, I have defined the symbolic variable tao. However, it still shows that undefined variable or functions. I didn't know where is wrong in the code.
The function is like this:
Ch = 0.8; H=0.6088;
syms t u s k tao
fsb= limit( symsum( (int( Ch*s^(1/2)*int((u-s)^(H-3/2)*u^(H-1/2),u,floor(t/tao)*tao,floor((t+tao)/tao)*tao),s,(k-1)*tao,k*tao ))^2,k,1,floor(t/tao)),tao,0) + ...
+limit( (int( Ch*s^(1/2)*int((u-s)^(H-3/2)*u^(H-1/2),u,s,floor((t+tao)/tao)*tao ),s,floor(t/tao)*tao,floor((t+tao)/tao)*tao) )^2,tao , 0);
fsb = matlabFunction(fsb);
sss=fsb(1);
I have tried change the path into the Matlab installed path, but it didn't work.
The fsb is a function defined by my self. It's a complicated function including integral and limit.
This is the information about the error:
undefined functions or variables 'tao'
symengine>#(t)limit(integral(#(s)sqrt(s).*integral(#(u)u.^(6.8e1./6.25e2).*1.0./(-s+u).^(5.57e2./6.25e2),s,tao.*floor((t+tao)./tao)).*(4.0./5.0),tao.*floor(t./tao),tao.*floor((t+tao)./tao)).^2,tao==0.0)+limit(symsum(integral(#(s)sqrt(s).*integral(#(u)u.^(6.8e1./6.25e2).*1.0./(-s+u).^(5.57e2./6.25e2),tao.*floor(t./tao),tao.*floor((t+tao)./tao)).*(4.0./5.0),tao.*(k-1.0),k.*tao).^2,k,1.0,floor(t./tao)),tao==0.0,Real)
I've got such a problem using MATLAB:
I wrote this function:
function E = f(x, lamda)
E = 1 - exp(-lamda * x);
end
When I write: Prob = f(1000, lamda); where lamda = 3.4274e-004
I get this error:
??? Attempted to access f(1000,0.000341565); index must be a positive integer or logical.
I understand that it requires a positive integer, but why ? I need lamda to be real. What's the problem here ? Can you, please, tell me where I'm wrong?
You have a function f and a variable f declared at the same time. Do clear f; then try your code again. What's happening here is that the variable declaration takes precedence over your function and so doing f would try and access the variable f first.
If you're using f as a variable somewhere and can't change this, then rename your function to be something other than f... perhaps... comp or something. Once you do this, make sure you change your file name so that it's called comp.m, then do:
Prob = comp(1000, lamda);
Your error message indicates that there is a variable called f in your workspace and matlab thinks you are trying to access its elements. Remove the variable f with clear('f') or rename the function to something else and you should be fine.
I have been using MATLAB fminunc function to solve my optimization problem. I want to try the minFunc package :
http://www.di.ens.fr/~mschmidt/Software/minFunc.html
When using fminunc, I defined a function funObj.m which gives me the objective value and the gradient at any point 'x'. It also takes in several external inputs say, {a,b,c} which are matrices. So the function prototype looks like :
function [objVal,G] = funObj(x,a,b,c)
I want to use the same setup in the minFunc package. From the examples, I figured this should work :
options.Method='lbfgs';
f = #(x)funObj(x,a,b,c);
x = minFunc(f,x_init,options);
But when I call this way, I get an error as:
Error using funObj
Too many output arguments.
What is the correct way to call minFunc for my case?
**EDIT : Alright, here is a sample function that I want to use with minFunc. Lets say I want to find the minimum of a*(b-x)^2, where a,b are scalar parameters and x being a scalar too. The MATLAB objective function will then look like :
function obj = testFunc(x,a,b)
obj = a*(b-x)^2;
The function call to minimize this using fminunc (in MATLAB ) is simply:
f = #(x)testFunc(x,a,b);
x = fminunc(f,x_init);
This gives me the minimum of x = 10. Now, How do I do the same using minFunc ?
"Note that by default minFunc assumes that the gradient is supplied, unless the 'numDiff' option is set to 1 (for forward-differencing) or 2 (for central-differencing)."
The error is because only one argument is returned by the function. You can either return the gradient as a second argument or turn on numerical differencing.
Agree with Mark. I think the simplest way to solve it is
minFunc(#testFunc, x_init, a, b, c)
In MATLAB temporary function can only have one return value. So f = #(x)testFunc(x,a,b); let your method drop gradient part every time. Because minFunc can accept extra paramters, you can pass a, b and c after x_init. I think this would work.
I created an anonymous function inside a script and I can't get MATLAB to run the fminsearch? Here's an what I have so far:
V=x(1);
f=x(2);
q=#(x) (pi.*D.*L)./(1000.*V.*f);
fminsearch(#q,x);
The variables D and L are defined, but MATLAB gives me the following error:
Error: File: Testing.m Line: 51 Column: 17
"q" was previously used as a variable, conflicting with its use here as the name of a function or command.
See "How MATLAB Recognizes Command Syntax" in the MATLAB documentation for details.
q is not mentioned before this command. What am I doing wrong?
Another thing that could solve my problem is to get my script to write a function file, but how to do that?
Remove the second #:
V=x(1);
f=x(2);
q=#(x) (pi.*D.*L)./(1000.*V.*f);
fminsearch(q,x);
q is a function handle. fminsearch expects a function handle. You can create a function handle out of a function using an # (e.g. #min), but you don't need to do that here.
You can also write the anonymous function inline with the search command:
V=x(1);
f=x(2);
fminsearch(#(x) (pi.*D.*L)./(1000.*V.*f),x);
UPDATE (credits to #wakjah)
For your code to do anything sensible, you should use the argument x of the anonymous function:
x0 = [initialV, initialF];
fminsearch(#(x) (pi.*D.*L)./(1000.*x(1).*x(2)), x0);
#function creates a function handle for an existing function.
q = #(x) whatever... creates a function handle called q.
But, you can't create a function handle for a function handle, only for a function.
See this:
>> fones = #ones
fones =
#ones
>> ffones = #fones
Error: "fones" was previously used as a
variable,
conflicting with its use here as the name
of a function or command.
See MATLAB Programming, "How MATLAB
Recognizes Function Calls That Use
Command Syntax" for details.
In Matlab, a function handle is a kind of a pointer to a function and is distinct from a function (unlike in some other languages where the a function identifier can be passed and stored as any other variable).
It's important to note that calling a function and a function handle results in the same behaviour. Except for the case where the identifier is used without any parentheses following it:
>> ones
ans =
1
>> fones
fones =
#ones
>> ones(2)
ans =
1 1
1 1
>> fones(2)
ans =
1 1
1 1
I am trying to write a minimal function that can be called with a variable number of arguments but that will not throw a wrong number of arguments error if miscalled.
Here is where I start from :
function varargout=fname(varargin)
% FNAME
% Usage: output=fname(input)
% Arguments check
if(nargin~=1 || nargout~=1)
disp('Function fname requires one input argument');
disp('and one output argument');
disp('Try `help fname`');
varargout(1:nargout)={0};
return;
end
input=varargin{1};
output=input;
varargout(1)={output};
end
However this does not work as I would like it to. Is there a way to write a function that :
never throw a "wrong number of arguments" error (so that the rest of the execution can continue)
accepts variable number of input and output arguments and checks them inside the function
(maybe more tricky) if the number of input / output arguments is not correct, does not replace the value of the provided output arguments (so that any misplaced call does not erase the previous value of the output argument)
I am open to any suggestions / other methods.
Thank you for your help.
UPDATE: thanks to #Amro for his answer, I guess what I miss here is either a call by address of reference for Matlab functions or a way to interrupt a function without returning anything and without stopping the rest of the execution.
Here is one way to implement your function:
function varargout = fname(input,varargin)
%# FNAME
%# Usage: output=fname(input)
%%# INPUT
if nargin<1
varargout(1:nargout) = {[]};
warning('Not enough input arguments.'), return
end
if ~isempty(varargin)
warning('Too many input arguments.')
end
%%# YOUR CODE: manipulate input, and compute output
output = input;
%%# OUTPUT
varargout{1} = output;
if nargout>1
warning('Too many output arguments.')
varargout(2:nargout) = {[]};
end
end
Obviously you can customize the warning messages to your liking...
Also, if you want your function to simply print the message instead of issuing warnings, replace all WARNING calls with simple DISP function calls.
Examples of function call:
fname()
fname(1)
fname(1,2)
x = fname()
x = fname(1)
x = fname(1,2)
[x,y] = fname()
[x,y] = fname(1)
[x,y] = fname(1,2)
The above calls execute as expected (showing warning messages when applicable). One caveat though, in the last three calls, if the variable y already existed in the workspace prior to the calls, it would be overwritten by the empty value y=[] in each...
If I understand your question correctly, then the answer is no. If a caller calls a function like this:
[a, b, c] = fname('foo');
then fname is required to return (at least) three outputs. There's no way to tell MATLAB that it should leave b and c alone if fname only returns one output.