如何计算Python中n个不同的独立同时投注的对数最大值?

How to calculate the logarithmic maximum of n different independent simultaneous bets in Python?

我正在尝试计算 n 不同投注的对数最大值。但是,对于这个例子,我有 2 个独立的同时投注。

  1. 投注 1 的获胜概率为 30%,小数赔率为 12.80。
  2. 投注 2 的获胜概率也为 30%,小数赔率为 12.80。

要计算 2 个独立同时投注的对数最大值,我需要计算出所有 4 种组合的概率:

  1. 投注 1 Winning/Bet 2 获胜
  2. 下注 1 Winning/Bet 2 输
  3. 投注 1 Losing/Bet 2 获胜
  4. 下注 1 Losing/Bet 2 输

假设 x0 是我投资组合中投注 1 的 0% 到 100% 之间的金额,而 x1 是我投注 2 中投资组合中 0% 到 100% 之间的金额,数学上可以通过最大化以下表达式来解决两个投注的最佳赌注: 0.09log(1 + 11.8x0 + 11.8x1) + 0.21log(1 + 11.8x0 - x1) + 0.21log(1 - x0 + 11.8x1) + 0.49log(1 - x0 - x1) 等于 x0: 0.214648, x1: 0.214648 (11.8 不是错字,它只是 12.8 - 1,利润)。

我曾尝试在 python 中实现此计算,但收效甚微。这是我需要帮助的当前代码:

from scipy.optimize import minimize
from math import log
from itertools import product
from sympy import symbols

Bets = [[0.3, 12.8], [0.3, 12.8]]

Odds = [([i[0], 1 - i[0]]) for i in Bets]
OddsList = list(product(Odds[0], Odds[1]))
#Output [(0.3, 0.3), (0.3, 0.7), (0.7, 0.3), (0.7, 0.7)]

Probability = []
for i in range(0, len(OddsList)):
    Probability.append(OddsList[i][0] * OddsList[i][1])
#Output [0.09, 0.21, 0.21, 0.49]

Win = [([i[1] - 1, - 1]) for i in Bets]
WinList = list(product(Win[0], Win[1]))
#Output [(11.8, 11.8), (11.8, -1), (-1, 11.8), (-1, -1)]

xValues = []
for j in range(0, len(Bets)):
    xValues.append(symbols('x' + str(j)))
#Output [x0, x1]

def logarithmic_return(xValues, Probability, WinList):
    Sum = 0
    for i in range(0, len(Probability)):
        Sum += Probability[i] * log (1 + (WinList[i][0] * xValues[0]) + ((WinList[i][1] * xValues[1])))
    return Sum

minimize(logarithmic_return(xValues, Probability, WinList))
#Error TypeError: Cannot convert expression to float

# However, when I do this, it works perfectly:
logarithmic_return([0.214648, 0.214648], Probability, WinList)
#Output 0.3911621722324154

这里的问题是 scipy.optimize.minimize 想要传递一个函数。您没有传递函数。您正在调用您的函数,并将其 return (浮点数)传递给 minimize.

你需要:

minimize( logarithmic_return, xValues, args=(Probability, WinList) )

看来这是您第一次将数字 Python 与符号混合使用。简而言之,您不能在符号表达式上使用数值函数(如 math.logscipy.optimize.minimize)。您需要先将符号表达式转换为 lambda 函数。

让我们尝试修复它:

from scipy.optimize import minimize
from itertools import product
from sympy import symbols, lambdify, log
import numpy as np

Bets = [[0.3, 12.8], [0.3, 12.8]]

Odds = [([i[0], 1 - i[0]]) for i in Bets]
OddsList = list(product(Odds[0], Odds[1]))
#Output [(0.3, 0.3), (0.3, 0.7), (0.7, 0.3), (0.7, 0.7)]

Probability = []
for i in range(0, len(OddsList)):
    Probability.append(OddsList[i][0] * OddsList[i][1])
#Output [0.09, 0.21, 0.21, 0.49]

Win = [([i[1] - 1, - 1]) for i in Bets]
WinList = list(product(Win[0], Win[1]))
#Output [(11.8, 11.8), (11.8, -1), (-1, 11.8), (-1, -1)]

xValues = []
for j in range(0, len(Bets)):
    xValues.append(symbols('x' + str(j)))
#Output [x0, x1]

def logarithmic_return(xValues, Probability, WinList):
    Sum = 0
    for i in range(0, len(Probability)):
        Sum += Probability[i] * log (1 + (WinList[i][0] * xValues[0]) + ((WinList[i][1] * xValues[1])))
    return Sum

# this is the symbolic expression
expr = logarithmic_return(xValues, Probability, WinList)
# convert the symbolic expression to a lambda function for
# numerical evaluation
f = lambdify(xValues, expr)
# minimize expect a function of the type f(x), not f(x0, x1).
# hence, we create a wrapper function
func_to_minimize = lambda x: f(x[0], x[1])
initial_guess = [0.5, 0.5]
minimize(func_to_minimize, initial_guess)

#      fun: -inf
# hess_inv: array([[1, 0],
#       [0, 1]])
#      jac: array([nan, nan])
#  message: 'NaN result encountered.'
#     nfev: 3
#      nit: 0
#     njev: 1
#   status: 3
#  success: False
#        x: array([0.5, 0.5])

如您所见,最小化有效。但是它没有找到任何解决方案。这是你要解决的问题。在这里,我只是提示您要最小化的函数的形状。