我正在寻找使用可变数量参数作为scipy中优化器输入的正确方法。
我有一组输入参数p1,...,pn,我用函数func(p1,...,pn)计算质量标准。我想最小化这个值。
输入参数为0或1表示应该使用它们。我不能简单地从参数列表中删除所有未使用的,因为我的质量标准函数要求它们为“0”以从方程中删除未使用的项。
def func(parameters):
...calculate one scalar as quality criteria...
solution = optimize.fmin_l_bfgs_b(func,parameters,approx_grad=1,bounds=((0.0, 5.0),...,(0.0,5.0)) # This will vary all parameters
在我的代码中,优化器运行时没有错误,但当然所有给定的参数都会更改以获得最佳解决方案。
有没有办法让... func的10个输入参数,但在优化器中只使用了5个?
到目前为止,我只能想到以一种不需要来自未使用参数的“0”输入的方式更改我的func定义。我会很感激如何避免这种想法。
非常感谢您的帮助!
答案 0 :(得分:1)
如果我理解正确,那么您要求的是最适合的约束,这样您就可以找到效果最好的[p0,p1,p2...p10]
,而不是为func()
找到最佳[p0, p1, ...p5]
。在func()
等条件下的函数p6=fixed6, p7=fixed7, p8=fixed8...
。
如果您在python
中使用args=(somthing)
,则可以将其转换为scipy.optimize.fmin_l_bfgs_b
代码。首先,编写一个部分修复的函数func_fixed()
def func_fixed(p_var, p_fixed):
return func(p_var+p_fixed)
# this will only work if both of them are lists. If they are numpy arrays, use hstack, append or similar
solution = optimize.fmin_l_bfgs_b(func_fixed,x0=guess_parameters,\
approx_grad=your_grad,\
bounds=your_bounds,\
args=(your_fixed_parameters), \ #this is the deal
other_things)
没有必要func_fixed()
,您可以使用lambda
。但这种方式读起来要容易得多。
答案 1 :(得分:0)
我最近解决了一个类似的问题,我希望在每次运行时优化不同的参数子集,但需要所有参数来计算目标函数。我在目标函数中添加了两个参数:
在目标函数中,我根据索引数组将参数列表设置为要优化的参数或初始值。
import numpy
import scipy.optimize
def objective_function(x_optimised, x_idx, x0):
x = []
j = 0
for i, idx in enumerate(x_idx):
if idx is 1:
x.append(x_optimised[j])
j = j + 1
else:
x.append(x0[i])
x = numpy.array(x)
return sum(x**2)
if __name__ == '__main__':
x_idx = [1, 1, 0]
x0 = [1.1, 1.3, 1.5]
x_initial = [x for i, x in enumerate(x0) if x_idx[i] is 1]
xopt, fopt, iter, funcalls, warnflag = scipy.optimize.fmin(objective_function, \
x_initial, args=(x_idx, x0,), \
maxfun = 200, full_output=True)
print xopt