【问题标题】:Finding unknowns in function from known output using Scipy/Python使用 Scipy/Python 从已知输出中查找函数中的未知数
【发布时间】:2018-02-14 16:20:58
【问题描述】:

我有以下 python 函数需要输入 a 和 b。

def interimfunc(x,y,z):
    #this is a dummy function - not a part of the actual question but included for completeness.
    #the actual function involves some statistical treatment - but that is not a problem here.
    sol = x*y+z
    return sol


def finalfunc(a, b):
    interimsol1 = interimfunc(0.4,a,b)
    interimsol2 = interimfunc(0.8,a,b)
    finalsol = interimsol1/interimsol2
    return finalsol

如果finalsol 是一个已知值。 如何通过求解非线性方程组找出未知数“a”和“b”??

===

发布此消息后,我得到了 4 票反对。我是一名机械工程师,正在学习计算机科学。我确实尝试在互联网上进行研究,但需要改进我的搜索 - 因此我在这里向专家提问。

===

除了上述等式 - 还有一个信息:

interimsol2 = interimfunc(0.8,a,b)

在哪里interimsol2 = 10 #i.e. known value 我们如何将这些新信息包含在我们未知的发现中?

===

@SergeyIvanov 下面要求的实际问题

def func(mu, sigma):
    tenpercent = st.norm.ppf(2, mu, sigma)
    ninetypercent = st.norm.ppf(2, mu, sigma)
    rfs = tenpercent/ninetypercent
    return rfs

【问题讨论】:

  • 你必须先做一些阅读。 a, b 是函数 finalfunc 的参数。您必须在调用函数时提供它们才能计算并返回输出finalsol。如果您想反转该过程并从finalsol 变为ab,则必须先进行数学运算。
  • 在我看来,finalsol 将永远是 0.5,无论您提供什么 ab。而且我不是数学家。这意味着产生它们的函数不是可逆的。所以你不能。如果你简化它,它归结为finalsol=0.4*a*b/(0.8*a*b),即finalsol=0.4/0.8=0.5
  • 在您当前的代码中,finalSol 值 = 0.5?
  • 你应该解方程 finalfunc(a, b) == known_solution,但不可能有两个未知变量
  • 请将初始问题从 "finalsol" 应等于特定值 更改为 "finalsol" 应等于一组特定值 (或类似的东西以确保正确性)

标签: python scipy


【解决方案1】:

我认为你应该求解一个非线性方程组。在两个已知解的两个方程的情况下,此代码应该可以解决您的问题(当然您可以扩展它):

from scipy.optimize import fsolve

known_values = [3,5]

def interimfunc(x,y,z):
    sol = x*y+z
    return sol

def finalfunc(a, b):
    interimsol1 = interimfunc(0.4,a,b)
    interimsol2 = interimfunc(0.8,a,b)
    finalsol = interimsol1/interimsol2
    return finalsol

def equations(p):
    a, b = p
    return (finalfunc(a,b) - known_values[0], # finalfunc(a,b) == solution1
            finalfunc(a,b) - known_values[1]) # finalfunc(a,b) == solution2

a, b =  fsolve(equations, (1, 1))# solution
print(a,b)
# -6192.07497308 5779.26987919

print(equations((a, b)))
# (1.0000003476651482, -0.99999965233485177) <-- bad convergence beacause there is no free paremeter in finalfunc.

但它只适用于相同的 known_values,这是没有意义的(解决方案将是 a 和 b 的随机组合)。问题是你应该有一些东西来区分两个方程 finalfunc (例如附加参数),因为你只能用不同的参数得到不同的解决方案。所以最后你应该有这样的东西:

from scipy.optimize import fsolve

def interimfunc(x,y,z):
    sol = x*y+z
    return sol

def finalfunc(a, b, c ):
    interimsol1 = interimfunc(0.4,a,b) + c
    interimsol2 = interimfunc(0.8,a,b) + c
    finalsol = interimsol1/interimsol2
    return finalsol


known_values = [0.8260869565217391,0.8333333333333334]


def equations(p):
    a, b = p
    return (finalfunc(a,b,0) - known_values[0], # finalfunc(a,b,c) == solution1
            finalfunc(a,b,1) - known_values[1]) # finalfunc(a,b,c) == solution2


a, b =  fsolve(equations, (1, 1))# solution
print(a,b)
print(equations((a, b)))
# 10.0 15.0 <-- correct values
# (4.4408920985006262e-16, 2.2204460492503131e-16) <-- good convergence

最后一个例子:

from scipy.optimize import fsolve
import scipy.stats as st

def equations(p):
    mu, sigma = p
    tenpercent = st.norm.ppf(2, mu, sigma)
    ninetypercent = st.norm.ppf(2, mu, sigma)
    return (ninetypercent - 500,
            tenpercent / ninetypercent - 1.0)

mu, sigma =  fsolve(equations,x0=(100, 10))# solution
print("mu, sigma:",mu, sigma)
print(equations((mu, sigma)))

这里的问题是ppf 可以生成nan 并破坏优化过程。所以猜测值应该非常谨慎地提出。

【讨论】:

  • 我们在第二个解决方案中假设finalsol 的值是多少?
  • 我自己解决了这个问题,得到了0.826086956521739100.83331。但是2 的值发生了变化...我们必须重新考虑如何解决这个问题。同时 - 这是 MathCad 上正在做的事情:engr.bd.psu.edu/forsman/metbd_050/Assignments/…
  • 我解释了为什么第一个解决方案不正确(技术上是,但实际上不是)。如果相同参数有不同的值,则应使用非线性最小二乘拟合。这是另一个故事。
  • 在您的示例中,0.4 和 0.5 只是一个函数中的常量。如果interimfunc(0.4,a,b) == value1interimfunc(0.8,a,b)==value2,你说的就是真的
  • 请通过电子邮件询问其他问题(sergei.v.ivanov at google mail)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-05-18
  • 2015-07-03
  • 2022-11-02
  • 1970-01-01
  • 2022-07-07
  • 1970-01-01
相关资源
最近更新 更多