thouska / spotpy

A Statistical Parameter Optimization Tool
https://spotpy.readthedocs.io/en/latest/
MIT License
247 stars 149 forks source link

SCEUA set parameter #297

Open dingxinjun opened 1 year ago

dingxinjun commented 1 year ago

spotpy.parameter.Uniform are generate param uniformly between lower and upper bound. how can i set the uniform to log uniform between log(-10) to log(10).

thouska commented 1 year ago

Hi @dingxinjun, thank you for your message. A log-uniform function is not yet part of the implemented parameter distributions in sptopy. But I guess it shouldn't be too hard to implement. One could build up e.g. on the implemented lognormal function and adjust it to be loguniform. @dingxinjun do you think you could provide a pull-request that works for your needs? I would be happy to merge and provide it with the next spotpy version.

thouska commented 1 year ago

I guess we would need to work with:

from scipy.stats import loguniform

and implement it accordingly in this super(..).init(...), right? The example looks like it's similar use to the implemented numpy.random stuff.

dingxinjun commented 1 year ago

class Uniform(Base): """ A specialization of the Base parameter for uniform distributions """ rndargs = 'low', 'high' def init(self, *args, *kwargs): """ :name: Name of the parameter :low: lower bound of the uniform distribution :high: higher bound of the uniform distribution :step: (optional) number for step size required for some algorithms, eg. mcmc need a parameter of the variance for the next step default is median of rndfunc(rndargs, size=1000) :optguess: (optional) number for start point of parameter default is quantile(0.5) - quantile(0.4) of rndfunc(rndargs, size=1000) """ super(Uniform, self).init(rnd.uniform, 'Uniform', args, **kwargs)

class loguniform(Base): """ A specialization of the Base parameter for uniform distributions """ rndargs = 'low', 'high' def init(self, *args, *kwargs): """ :name: Name of the parameter :low: lower bound of the uniform distribution :high: higher bound of the uniform distribution :step: (optional) number for step size required for some algorithms, eg. mcmc need a parameter of the variance for the next step default is median of rndfunc(rndargs, size=1000) :optguess: (optional) number for start point of parameter default is quantile(0.5) - quantile(0.4) of rndfunc(rndargs, size=1000) """ super(loguniform, self).init(loguniform, 'loguniform', args, **kwargs)

i just follow the uniform class but it does not work, Can you give me a pre-release version of log uniform

dingxinjun commented 1 year ago

i have import scipy package but not deal with it, sorry im not familiar with the parameter class,can't handle it

thouska commented 1 year ago

No worries, I implemented a branch with has a pre-release version, but haven't tested it. Would you like to have a look? https://github.com/thouska/spotpy/blob/Lognormal-implementation/src/spotpy/parameter.py#L294

thouska commented 1 year ago

Oh, yes seems like the scipy loguniform function comes with different methods. I implemented the rvs (random vairates) method and updated the code linked above. That should work now. But is it, what you need?

dingxinjun commented 1 year ago

i just want test sce algorism parameter.loguniform instead of parameter.uniform

dingxinjun commented 1 year ago

it work now a param low boundary i set to 0 ,i change 0 to 0000000001,it works

thouska commented 1 year ago

Nice, that it works now. And yes, given the nature of log it makes sense that it is producing an error with a setting of zero. The same will happen with negative values/boundaries.

thouska commented 1 year ago

Cool, if it's okay for you, I will wait with the merge, until I am working on a new spotpy version. But let me know, if you need it in an official version earlier. Currently, I am not working on any data assimilation program. But I can let you know if I do.