我是Pyomo和Ipopt的新手。我想用这些工具优化一个非线性优化问题,在优化一个函数时出现错误。
我一直在玩Pyomo提供的例子。我的问题的主要区别在于,我想在一个单独的函数中定义目标函数,并且它意味着一些与numpy数组的乘法,但我认为这两个问题都可以用Pyomo处理。
我已经尽量简化了我的问题(从优化的角度来看,这肯定是没有意义的,但这只是为了说明问题)。我的问题是这样的。
import numpy as np
from pyomo.environ import *
def myfunc(model, extra_param):
matrix_A=np.sin(np.random.rand(100,100))+extra_param
return sum(model.x*matrix_A-extra_param)
extra_param=5
model = ConcreteModel()
model.IDX=range(100)
model.x = Var(model.IDX,bounds=(0,1.), initialize=0.99)
model.obj=Objective(expr = myfunc(model,extra_param))
model.pprint()
solver = SolverFactory('ipopt')
solver.solve(model, tee=True)
我得到以下信息
Ipopt 3.11.1: C:\Users\A\Anaconda3\Library\bin\ipopt.exe: jacdim: got M = 0, N = 0, NO = 1
ERROR: Solver (ipopt) returned non-zero return code (1)
ERROR: See the solver log above for diagnostic information.
你遇到的问题是由于你的目标函数没有返回一个导致标量值的表达式(你可以通过查看 model.obj.pprint()
).
像这样的东西可能会做你想要的。
def myfunc(model, extra_param):
matrix_A=np.sin(np.random.rand(100,1)).flatten() + extra_param
return sum(matrix_A[i] * model.x[i] for i in model.IDX)
注意,我把 (100,100)
在你 np.random.rand
功能与 (100,1)
,因为你的变量 model.x
是一个矢量。此外, .flatten()
方法会将数组折叠成1-D。