MATLAB: Variable number of inputs in a function

inputs

I am using ML estimation. If I have initial values par0, data in a matrix mData and if I need to find 2 parameters par(1) and par(2) that maximise the likelihood function, it looks like this:
fLL = @(par) - fLogLik(par(1),par(2),mData);
[par, fval, eflag] = fmincon(fLL,par0,[],[],[],[],[iLb iLb],... % Calls the optimisation function
[iUb iUb],[],options);
where the iLB and iUb are used defined lower and upper bounds.
Now, this works fine. My issue is that I want to make this completely general. Sometimes I need 2 parameters, other times I need, say, 4. When 4 are needed, I'd have:
fLL = @(par) - fLogLik(par(1),par(2),par(3),par(4),mData);
[par, fval, eflag] = fmincon(fLL,par0,[],[],[],[],[iLb iLb iLb iLb],... % Calls the optimisation function
[iUb iUb iUb iUb],[],options);
How can I implement this in an efficient way (assuming that I have a variable before this, say iS, with the number of parameters)? Also, the same problem happens again insided the fLogLik function, which uses a matrix mQ as an input. This matrix is defined as :
mQ = diag(par1,par2,par3,...)
The bit
[iLb iLb iLb iLb]
is easy to handle by defining
iLb * ones(1,iS).
I am just not sure about how to specify the number of parameters in fLogLik as a function of iS.

Best Answer

Matlab has a well defined method for passing variable numbers of arguments to functions, using expansion of cell arrays into comma separated lists. You would thus have to transform your input matrix into a cell array, then expand that cell array into a c-s-l.
Now, the best place to do that conversion would be inside fLogLik keeping the par as an array until then, so your anonymous function becomes
fLL = @(par) - fLogLik(par, mData);
and fLogLik:
function x = fLogLik(par, mData)
%...



par = num2cell(par); %convert to cell array

mQ = diag(par{:}); %expand cell array to comma-separated list.
%...
end
If you really insist that fLogLik must have a variable numbers of arguments, then a) you need to change the order so that the fixed argument mData is first, then use varargin for the variable arguments:
function x = fLogLik(mData, varargin)
%...
mQ = diag(varargin{:});
%...
end
b) You have to do the conversion from matrix to cell array in fLL.Unfortunately, matlab chaining rules prevents you from doing that into an anonymous function. Thus, you'll have to use a standard function. A nested function would be best if you want to use your iS and mdata variables, although iS is not really needed in the body of the function except maybe for validation:
iS = 4;
function x = fLL(par)
assert(numel(par) == iS, 'Wrong size of array passed to function'); %if validation desired
par = num2cell(par); %convert to cell array
x = fLogLik(mdata, par{:}); %expand cell array into comma separated list
%matlab chaining rules prevent using : num2cell(par){:}
end