Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

parameters problem in FindFit

368 views
Skip to first unread message

gyz...@139.com

unread,
Oct 15, 2008, 5:37:40 AM10/15/08
to
Hi, guys :
I get a list like this :
lis = {{12.5, 1.146}, {32, 1.145}, {50,
1.144}, {69, 1.1424}, {84.6,
1.139}}
My aim is :
FindFit[lis,
a - (b x^2)/(c + x), {{a, 1.14}, {b, 0.0003}, {c, 300}}, x]
As we can see, I want this list to be fitted using parameters a, b, c
around 1.14, 0.0003, 300. However Mathematica gives { b, 10^8} and {c,
10^14} far from what I expect.I set "MaxIterations" to less times,
but it doesn' t make sense.
My friends didn't give the answer either, I am here for your advice.
Thanks in advance.

Richard Hofler

unread,
Oct 16, 2008, 5:04:15 AM10/16/08
to
Hi,

You'll probably get many similar answers. The Mathematica Documentation
Center says this:

FindFit[data,{expr,cons},pars,vars]
finds a best fit subject to the parameter constraints cons.

So, add constraints to your function.

In[5]:= FindFit[lis, {a - (b x^2)/(c + x), {1.13 < a < 1.15,
.0001 < b < .0004, 299 < c < 301}}, {a, b, c}, x]

Out[5]= {a -> 1.14624, b -> 0.00035099, c -> 299.942}

I hope this helps.

Richard Hofler

Jean-Marc Gulliet

unread,
Oct 16, 2008, 5:04:26 AM10/16/08
to
gyz...@139.com wrote:

> I get a list like this :
> lis = {{12.5, 1.146}, {32, 1.145}, {50,
> 1.144}, {69, 1.1424}, {84.6,
> 1.139}}
> My aim is :
> FindFit[lis,
> a - (b x^2)/(c + x), {{a, 1.14}, {b, 0.0003}, {c, 300}}, x]
> As we can see, I want this list to be fitted using parameters a, b, c
> around 1.14, 0.0003, 300. However Mathematica gives { b, 10^8} and {c,
> 10^14} far from what I expect.I set "MaxIterations" to less times,
> but it doesn' t make sense.

If you plot your model with the parameters returned by FindFit, you will
see that the fit is quite good. OTHO, the choice of 300 for c seems to
be a poor choice (except if you have some compelling reason from the
physical situation your are modeling). Anyway, try to use different
methods as illustrated below and check the result on a graph.

In[1]:= lst = {{12.5, 1.146}, {32, 1.145}, {50, 1.144}, {69,
1.1424}, {84.6, 1.139}};

In[2]:= model = a - (b x^2)/(c + x);

In[3]:= sol =
FindFit[lst, model, {{a, 1.14}, {b, 0.0003}, {c, 300}}, x]

Out[3]= {a -> 1.14624, b -> 2.45466*10^8, c -> 2.59133*10^14}

In[4]:= solar =
FindFit[lst, model, {a, b, c}, x,
Method -> #] & /@ {"ConjugateGradient", "Gradient",
"LevenbergMarquardt", "Newton", "QuasiNewton"}

During evaluation of In[4]:= FindFit::lstol: The line search \
decreased the step size to within tolerance specified by AccuracyGoal \
and PrecisionGoal but was unable to find a sufficient decrease in the \
norm of the residual. You may need more than MachinePrecision digits \
of working precision to meet these tolerances. >>

Out[4]= {{a -> 1.14769, b -> 0.0000906534,
c -> 1.01529}, {a -> 1.14769, b -> 0.0000906534,
c -> 1.01529}, {a -> 1.14624, b -> 1.49101*10^8,
c -> 1.57403*10^14}, {a -> 1.14388, b -> 9.6559*10^-6,
c -> -37.5354}, {a -> 1.14769, b -> 0.0000906531, c -> 1.01317}}

In[5]:= Plot[{model /. sol, model /. solar[[1]],
model /. {a -> 1.14, b -> 0.0003, c -> 300}}, {x, 10, 100},
Epilog -> Point /@ lst]

In[6]:= sol =
FindFit[lst, model, {{a, 1.14}, {b, 0.0003}, {c, 300}}, x,
Method -> #] & /@ {"ConjugateGradient", "Gradient",
"LevenbergMarquardt", "Newton", "QuasiNewton"}

During evaluation of In[6]:= FindFit::lstol: The line search \
decreased the step size to within tolerance specified by AccuracyGoal \
and PrecisionGoal but was unable to find a sufficient decrease in the \
norm of the residual. You may need more than MachinePrecision digits \
of working precision to meet these tolerances. >>

During evaluation of In[6]:= FindFit::lstol: The line search \
decreased the step size to within tolerance specified by AccuracyGoal \
and PrecisionGoal but was unable to find a sufficient decrease in the \
norm of the residual. You may need more than MachinePrecision digits \
of working precision to meet these tolerances. >>

During evaluation of In[6]:= FindFit::lstol: The line search \
decreased the step size to within tolerance specified by AccuracyGoal \
and PrecisionGoal but was unable to find a sufficient decrease in the \
norm of the residual. You may need more than MachinePrecision digits \
of working precision to meet these tolerances. >>

During evaluation of In[6]:= General::stop: Further output of \
FindFit::lstol will be suppressed during this calculation. >>

Out[6]= {{a -> 1.14637, b -> 0.000365391, c -> 300.}, {a -> 1.14637,
b -> 0.000365391, c -> 300.}, {a -> 1.14624, b -> 2.45466*10^8,
c -> 2.59133*10^14}, {a -> 1.14624, b -> 4.13776,
c -> 4.36807*10^6}, {a -> 1.14637, b -> 0.000365391, c -> 300.}}

HTH,
-- Jean-Marc


Ray Koopman

unread,
Oct 16, 2008, 5:05:10 AM10/16/08
to

f[c_] := Abs[QRDecomposition[{1,#[[1]]^2/(c+#[[1]]),#[[2]]}& /@
lis][[2,-1,-1]]]

gives the square root of the residual sum of squares, minimized with
respect to a & b for a given value of c. Plotting f[c] shows a local
minimum at about -8.6, but the overall minimum appears to be at c ->
Infinity.

dh

unread,
Oct 16, 2008, 5:05:54 AM10/16/08
to

Hi,

what do you know about noise in your data. Usually you have some

measurement noise. In this case you need more points to fit 3 parameters.

Further, do you have any reason for the proposed functional form? It

does not seem to fit the data well.

Question is, if the S-shape is noise or real. If it is real, it looks

like a cubic function. If is noise, you need more points.

Mathematica does the best it can. Try plotting the curve with the parameters you

prefer and you will see that you get it completely wrong.

hope this helps, Daniel

gyz...@139.com wrote:

> Hi, guys :

> 1.139}}

> My aim is :

> FindFit[lis,

> Thanks in advance.

>

--

Daniel Huber

Metrohm Ltd.

Oberdorfstr. 68

CH-9100 Herisau

Tel. +41 71 353 8585, Fax +41 71 353 8907

E-Mail:<mailto:d...@metrohm.com>

Internet:<http://www.metrohm.com>

annetts729

unread,
Oct 16, 2008, 5:06:27 AM10/16/08
to
Hi,
Hi,

Did you look at FindFit's Method option?

Regards,

Dave.

Bill Rowe

unread,
Oct 16, 2008, 5:06:38 AM10/16/08
to
On 10/15/08 at 5:37 AM, gyz...@139.com wrote:


>I get a list like this : lis = {{12.5, 1.146}, {32, 1.145}, {50,
>1.144}, {69, 1.1424}, {84.6, 1.139}}
>My aim is :

>FindFit[lis, a - (b x^2)/(c + x), {{a, 1.14}, {b, 0.0003}, {c,
>300}}, x]

>As we can see, I want this list to be fitted using parameters a, b,
>c around 1.14, 0.0003, 300. However Mathematica gives { b, 10^8} and

>{c,10^14} far from what I expect.I set "MaxIterations" to less times,


>but it doesn' t make sense.

Welcome to the world of non-linear fitting.

When you say the result doesn't make sense I assume you mean
from the perspective of some other knowledge about the data
being fitted by this model.

For large values of c your model approaches

a - d x^2 where d = b/c. And as you can see from

In[27]:= sol =
FindFit[lis,
a - (b x^2)/(c + x), {{a, 1.14}, {b, 0.0003}, {c, 300}}, x];
b/c /. sol

Out[28]= 9.47257*10^-7

In[29]:= FindFit[lis, a - (d x^2), {{a, 1.14}, {d, 0.0003}}, x]

Out[29]= {a->1.14624,d->9.47257*10^-7}

=46indFit is effectively fitting this reduced model to your data.

Plotting the data shows the result is nearly a linear function
of x. So, an alternative would be to do:

In[30]:= FindFit[lis,
a - (b x^2)/(c + x), {{a, 1.14}, {b, 1}, {c, 0}}, x]

Out[30]= {a->1.14544,b->0.0000361511,c->-16.6034}

Doing non-linear fitting is inherently a difficult problem. In
your particular case, the difficulty is increased by the very
small variation in dependent variable and the fact the model
reduces to simpler models for some extreme values of the unknown parameters=
.

You might have better success by transforming either the
dependent or independent variable or both and fitting a
different model to the transformed data.

0 new messages