MATLAB Answers

Output argument "XXX" (and maybe others) not assigned during call to "function".

423 views (last 30 days)
Hello, I've created this function, but every time I try to run it returns me the error:
Output argument "XXX" (and maybe others) not assigned during call to "function".
I can't find what is my mistake. Im assigning the variable.
function Img_out = escres(I,f,c)
A=ceil(log2(f));
B=ceil(log2(c));
[fo, co]=size(I);
It=Component_Transformation(I,'FR');
%%Aumento de tamaño
if (f>fo && c>co)
for n=1:3
Iw=wavelift(It(:,:,n),3,'cdf97');
If=zeros(2^A,2^B,3);
If(1:fo,1:co,n)=Iw;
end
for n=1:3
If(:,:,n)=wavelift(If(:,:,n),-3,'cdf97');
end
Img_out=If;
end

  2 Comments

Devin Bautista-Leaf
Devin Bautista-Leaf on 7 Oct 2018
this is a problem I encounter more often than I would like. I have found it is typically due to one of two things:
1.) you forgot to put your function output in the function script example:
function [outputs] = call_name(inputs)
if
end%if
***
end % function
the location of the star marks where you should have put the output names. so it should look like this:
function [outputs] = call_name(inputs)
if
end%if
output_1=parameter;
end % function
2.) you have satisfied the above criteria and now you are still getting this error. I find this extremely frustrating because there is no way to know what is wrong. In my experience this means I made a mistake in my function. For some reason Matlab would rather give me this error than tell me I made a mistake.
For example I was just writing a function and got this error. Here was my script:
function [xv,yv,iv] = OT1P7_1(f,gradf,x0,tol)
%f in the form of anynomous i.e. f=@(x) 2*x(1)*x(2)^2
% gradf in the from as a two row vector where one component is the ?f/?x and
% the next as ?f/?y i.e. f=@(x) [2*x(2)^2;4*x(1)*x(2)] or in the general
% form: f=@(x) [?f/?x;?f/?y]
% x0 in the same form as the gradf. A two row matrix with constant numbers
% filling them [#1;#2], i.e. [1;5].
% tol is just a number that we will use as a measure of absolute error allowed
i=0;
x=x0;
while norm(gradf(x))<tol
after messing around I then realized I meant to fix something in my function. so I made the following correction in my while statement then ran it again:
function [xv,yv,iv] = OT1P7_1(f,gradf,x0,tol)
%f in the form of anynomous i.e. f=@(x) 2*x(1)*x(2)^2
% gradf in the from as a two row vector where one component is the ?f/?x and
% the next as ?f/?y i.e. f=@(x) [2*x(2)^2;4*x(1)*x(2)] or in the general
% form: f=@(x) [?f/?x;?f/?y]
% x0 in the same form as the gradf. A two row matrix with constant numbers
% filling them [#1;#2], i.e. [1;5].
% tol is just a number that we will use as a measure of absolute error allowed
i=0;
x=x0;
while norm(gradf(x))>=tol
interestingly enough this is the only correction I made to my function and it seemed to appease the error. I am not sure if this will help anyone but know if you have satisfied the first condition the reason its not working is most likely due to Matlab stupidity and you need to make some sort of correction Matlab is unwilling to tell you about.
Walter Roberson
Walter Roberson on 11 Oct 2018
"if you have satisfied the first condition the reason its not working is most likely due to Matlab stupidity"
No, the reason it would not work would be that your code does not assign a value to the required variable. Consider
function y = something(x)
while x > 1
y = x;
x = x - 1;
end
Now invoke
disp(something(1))
That would make x = 1 inside the function. 1 > 1 is false, so the body of the while loop would not be executed at all, so nothing would be assigned to y, leading to a problem when y had to be returned to the calling environment in order to be displayed.
If the code had instead been
function y = something(x)
while x >= 1
y = x;
x = x - 1;
end
then something(1) would first test 1 >= 1 and a value would be assigned to y in that case. The adjusted code would still be flawed for (for example) something(-3), but the point is still easy to see: that the conditions associated with while or if can make real differences as to whether your code happens to assign to a particular variable or not. This is not MATLAB stupidity: this is the programmer not accounting for all possibilities.

Sign in to comment.

Accepted Answer

Walter Roberson
Walter Roberson on 23 Oct 2016
You only assign to Img_out if (f>fo && c>co) . In the situation where one or both of those conditions are not true, you never assign to Img_out

  3 Comments

Walter Roberson
Walter Roberson on 23 Oct 2016
In cases where the code ends up being compiled, such as for MATLAB Coder or a Simulink MATLAB Function Block in any acceleration mode other than Normal, then the code generation notices that the result can be undefined and refuses to generate code -- because although for one call to the routine you might be sure that the condition will be true, the code generation facility can't be sure that it will always be true.
If the condition is guaranteed to be true, then you can omit the if, and perhaps add assert() to cause failure for the unhandled case. If the condition is not guaranteed to be true, then make sure that the output variable is assigned something in the case that the condition is not true.
Are you certain that the condition is true? We do not know what the routine Component_Transformation does, but considering that you expect the output from Component_Transformation to have at least 3 dimensions, it would be entirely plausible that you expect the input I to be 3 dimensional. But you have
[fo, co]=size(I);
In the case where you have two outputs to size(), then the output values of size() are defined to be
temp = size(I);
fo = temp(1);
co = prod(temp(2:end));
If I is an RGB image, that would leave fo as the number of rows, and would leave co as 3 times the number of columns. Are you certain that your inputs for f and c satisfy (f>fo && c>co) taking that into consideration?
Please re-read the definition of size for multiple output arguments. You were probably expecting that
[fo, co]=size(I)
mean fo = size(I,1) and co = size(I,2) but that is not how it is defined. The product of all of the outputs from size() is always equal to the number of elements in the input, so if you have too few outputs then the last one contains the the product of everything not already accounted for.
Alan Guadalupe Cano
Alan Guadalupe Cano on 23 Oct 2016
Thank you, the problem was the size function and the condition in the if. I changed the line of the size for this:
[fo, co, ~]=size(I);
In that way I got the correct values (Files and columns of the image) and now the conditions in the if are correctly checked.
Thank you so much for your help.

Sign in to comment.

More Answers (1)

Med Aymane Ahajjam
Med Aymane Ahajjam on 23 Jul 2019
Had the same problem several times honestly. The reason is always an input not being appropriate for the logic in the function.
For example I had a switch case function. It took 3 inputs and outputs 1 result for each case. The problem was in all except one case the result was assigned to a double. That one case was taking a control's value that was a string. The problem was solved when I used str2double to that line.

  4 Comments

Show 1 older comment
Walter Roberson
Walter Roberson on 3 May 2020
Mario, that could would fail if x is not a scalar, unless x happened to be all the same case (for example, all >=3 ) . If you have a mix of cases, then although some x < -2, not all of them would be, and then if x<-2 would fail. In MATLAB, when you use an if like that, MATLAB does not calculate "corresponding" values according to which entries match which conditions.
If you have a non-scalar input, you can loop internally, or you can arrayfun internally, or you can use logical indexing (which is the recommended approach.)
Walter Roberson
Walter Roberson on 3 May 2020
My funtion is a subrutine of other program.
That does not tell us that x is definitely scalar.
Insert this as the first line, before the if
assert(isscalar(x), 'AiryAi, x is not scalar')

Sign in to comment.

Products