Hi,
Mark Harder wrote:
>
> Just to set the stage, I am trying to use NonlinearRegression
> (again, alas) to fit a model with shared parameters to 2 sets of data,
> which are distinguished from each other by an integer index which
> appears in the data list in the NLR arguments as an extra independent
> variable, which will be passed to the model function in the usual
> fashion. This simple scheme fails, although I have tried several
> alternative formulations of the model function because, apparently, NLR
> is unable to pass the integer index into the model function. I have
> enclosed a trial function which reproduces this behavior. I hope
> someone can show me what I am doing "wrong" and how I can fix my
> problem:
>
> (* definition of function *)
>
> In[478]:=
> Clear[trialfn, i, ii, c, cc];
> trialfn[aN_List, c, i] := (Print[i];
> Return[c*aN\[LeftDoubleBracket]i\[RightDoubleBracket]] )
c and i should be a Pattern[] and the Return[] is useless
because the function value will be the last evaluated expression
Clear[trialfn, i, ii, c, cc];
trialfn[aN_List, c_, i_Integer] := (Print[i];c*aN[[i]])
>
> (* aN is a list *)
>
> In[405]:= {aN1,aN2};
>
> {c, i, aN}
> Out[405]= {c, i, {aN1, aN2}}
>
> (* pass numeric values explicitly *)
>
> In[482]:=
> trialfn[{-3.4, -4.}, 0., 1 ]
> Out[482]=
> trialfn[{-3.4, -4.}, 0., 1] (* Doesn't understand command *)
With your definition the pattern will only match for a variables c and
i that have no values.
>
> (* passed by replacement ( I think this is how NLR does it) *)
>
> In[487]:=
> trialfn[aN, c, i ] /. {aN1 -> -3.4`, aN2 -> -4.`, c -> 1.`, i -> 2`}
> an integer nor a list \
> of integers."
> Out[487]= -4. (* correct evaluation, for i=2!! *)
It is not the correct evaluation. first trialfn[aN,c,i] is evaluated and
gives c*aN[[i]]. Since i has no value you get an error message and than
the ReplaceAll insert the numeric value for i into c*aN[[i]] and gives
you the result.
>
> note the result of printing out the value of i, although the function
> *is* evaluated. This doesn't work in NLR, however:
>
> fitData2 = {{0, 1, -3.320248485`}, {1, 1, -3.215648485`}, {2,
> 1, -3.375939394`}, {0, 2, -4.312424242`}, {1, 2, -3.985844444`},
> {2,
> 2, -4.300822222`}}; (* trial data for fitting *)
>
> In[476]:= best3D = NonlinearRegress[fitData2, trialfn[aN, c, i ]
> ,
> {c, i}, { {aN1, {-3.4, -3.}}, {aN2, {-4., -3.}} },
> Method -> Gradient, Compiled -> False]
>
> an integer nor a list \
> of integers.
>
> "From In[476]:=
> FindMinimum::"fmgs": "Could not symbolically find the gradient of
> \!\(#1\\ \(\
> \(\(\({aN1, aN2}\)\) \[LeftDoubleBracket] #2
> \[RightDoubleBracket]\)\)\). Try \
> using the default method, giving two starting values for each variable."
This is no wonder, because Part[] will never have a derivative with
respect
to i. But you give {c, i} as variables *and* say that a gradient with
respect to both variables should be evaluated.
What do you want ? Mathematica has no algorithms for integer
optimization.
If you wish to have two function you should fit against a linear
combination
of the two functions, if you wisth to fit to function 1 *or* function 2
you should do two fits't and look for the smaller residual.
Regards
Jens