lmfit / lmfit-py

Non-Linear Least Squares Minimization, with flexible Parameter settings, based on scipy.optimize, and with many additional classes and methods for curve fitting.
https://lmfit.github.io/lmfit-py/
Other
1.07k stars 275 forks source link

Bug when setting expression for a parameters object resulting in crash #516

Closed wallo-zz closed 5 years ago

wallo-zz commented 5 years ago

I encountered this bug recently while trying to make a fit on some experiment results i got. The error results from trying to set a specific parameter using an expression which is equal to that same specific parameter. Then using this parameter in a model to fit will result in the kernel dying.

Since this bug resulted in the kernel dying and then restarting, I had no idea where to look and thus it took me quite some time before I noticed what went wrong. I reckon it would be very helpful to add some try catch block so that the kernel does not die and a useful error can be given.

Since the kernel died, I cannot supply a traceback.

Python: 3.6.5 |Anaconda, Inc.| (default, Mar 29 2018, 13:32:41) [MSC v.1900 64 bit (AMD64)]

lmfit: 0.9.11, scipy: 1.1.0, numpy: 1.14.3, asteval: 0.9.13, uncertainties: 3.0.3, six: 1.11.0

from lmfit import Parameters from lmfit.models import GaussianModel

pars = Parameters()

x = [0, 1, 2, 3, 4, 5, 6] y = [0, 1, 3, 5, 3, 1, 0]

model = GaussianModel() pars.update(model.make_params()) pars["amplitude"].set(expr="testpar * sigma") pars.add("testpar", 0) pars["testpar"].set(expr="testpar")

out = model.fit(y, pars, x=x)

newville commented 5 years ago

@wallo-zz Please use the mailing list for questions about lmfit. The instructions are pretty clear on this. I don't know why your "kernel" (Jupyter, something else?) is dying, but it's their problem. The script you posted will (correctly, BTW) raise a RecursionError. That should not kill the kernel. But also, whatever kernel you are using is not Python -- it is an interface to Python. So, if "the kernel is dying" you should try using normal Python.

The recursion error comes correctly because you have

pars["testpar"].set(expr="testpar")

which means "set the value for the parameter testpar to be evaluated from the expression 'testpar'". That is recursive, and probably not what you want. Setting it to 0 is probably also not what you want.

Again, use the mailing list for questions about lmfit.