optimization - 如何在最小化目标参数的同时重新评估 Gekko 目标
问题描述
提前道歉,我刚开始学习Gekko,看看我是否可以将它用于项目。我正在尝试在玩游戏状态非常有限(50 ^ 2)和每回合选项(0-10 包括在内)的游戏时优化胜率。
据我了解,我可以使用m.solve()
Gekko 功能来最小化我在这里设置的对手的赢率:
PLAYER_MAX_SCORE = 50 #Score player needs to win
OPPONENT_MAX_SCORE = 50 #Score opponent needs to win
#The opponent's current strategy: always roll 4 dice per turn
OPPONENT_MOVE = 4
m = GEKKO()
m.options.SOLVER = 1
"""
player_moves is a 2-d array where:
- the row represents player's current score
- the column represents opponent's current score
- the element represents the optimal move for the above game state
Thus the player's move for a game is player_moves[pScore, oScore].value.value
"""
player_moves = m.Array(m.Var, (PLAYER_MAX_SCORE, OPPONENT_MAX_SCORE), value=3, lb=0, ub=10, integer=True)
m.Obj(objective(player_moves, OPPONENT_MOVE, PLAYER_MAX_SCORE, OPPONENT_MAX_SCORE, 100))
m.solve(disp=False)
作为参考,objective
是一个函数,它根据当前玩家的行为(在 中表示)返回对手的胜率player_moves
。
唯一的问题是 m.solve() 只调用一次目标函数,然后立即返回player_moves
数组中的“已解决”值(结果只是定义时的初始值player_moves
)。我希望 m.solve() 多次调用目标函数来确定新对手的胜率是下降还是上升。
Gekko 可以做到这一点吗?或者对于这类问题我应该使用不同的库吗?
解决方案
Gekko 创建了一个优化问题的符号表示,它被编译成字节码。因此,目标函数必须用 Gekko 变量和方程来表示。对于不使用 Gekko 变量的黑盒模型,另一种方法是使用scipy.optimize.minimize()
. 有一个Gekko 和 Scipy 的比较。
西皮
import numpy as np
from scipy.optimize import minimize
def objective(x):
return x[0]*x[3]*(x[0]+x[1]+x[2])+x[2]
def constraint1(x):
return x[0]*x[1]*x[2]*x[3]-25.0
def constraint2(x):
sum_eq = 40.0
for i in range(4):
sum_eq = sum_eq - x[i]**2
return sum_eq
# initial guesses
n = 4
x0 = np.zeros(n)
x0[0] = 1.0
x0[1] = 5.0
x0[2] = 5.0
x0[3] = 1.0
# show initial objective
print('Initial Objective: ' + str(objective(x0)))
# optimize
b = (1.0,5.0)
bnds = (b, b, b, b)
con1 = {'type': 'ineq', 'fun': constraint1}
con2 = {'type': 'eq', 'fun': constraint2}
cons = ([con1,con2])
solution = minimize(objective,x0,method='SLSQP',\
bounds=bnds,constraints=cons)
x = solution.x
# show final objective
print('Final Objective: ' + str(objective(x)))
# print solution
print('Solution')
print('x1 = ' + str(x[0]))
print('x2 = ' + str(x[1]))
print('x3 = ' + str(x[2]))
print('x4 = ' + str(x[3]))
壁虎
from gekko import GEKKO
import numpy as np
#Initialize Model
m = GEKKO()
#initialize variables
x1,x2,x3,x4 = [m.Var(lb=1,ub=5) for i in range(4)]
#initial values
x1.value = 1
x2.value = 5
x3.value = 5
x4.value = 1
#Equations
m.Equation(x1*x2*x3*x4>=25)
m.Equation(x1**2+x2**2+x3**2+x4**2==40)
#Objective
m.Minimize(x1*x4*(x1+x2+x3)+x3)
#Solve simulation
m.solve()
#Results
print('')
print('Results')
print('x1: ' + str(x1.value))
print('x2: ' + str(x2.value))
print('x3: ' + str(x3.value))
print('x4: ' + str(x4.value))
推荐阅读
- sql-server - SQL Server:为最有效的大小创建表列
- javascript - {foo = foo} 验证技巧是在解构要采用的安全模式吗?
- flutter - 滑过时颤振滑块不更新
- c# - 使用 D-Bus 和 .Net Core 的蓝牙 GATT 服务器
- jsf - 如何在 JSF 中输入时间值
- image - 该页面无法在我的颤振应用程序中正确加载页面(更新)无效参数:源不得为空
- php - 通过 AJAX 调用返回自动编号 ID MySQL?
- forms - 将 Flex URLRequest 和 navigateToURL 表单模拟重新编码为 Royale JS
- python - 将 TFLite (TensorFlow) 转换为 MLModel (Apple)
- jquery - 在 wordpress 中切换类