我正在尝试使用scipy.optimize
来最小化一个复(向量)变量的函数。目前为止,我的结果表明这可能是不可能的。为了研究这个问题,我实现了一个简单的例子-最小化一个带偏移量的复向量的2-范数:
import numpy as np
from scipy.optimize import fmin
def fun(x):
return np.linalg.norm(x - 1j * np.ones(2), 2)
sol = fmin(fun, x0=np.ones(2) + 0j)
输出为
Optimization terminated successfully.
Current function value: 2.000000
Iterations: 38
Function evaluations: 69
>>> sol
array([-2.10235293e-05, 2.54845649e-05])
显然,解决办法应该是
array([0.+1.j, 0.+1.j])
对这个结果感到失望,我还尝试了scipy.optimize.minimize
:
from scipy.optimize import minimize
def fun(x):
return np.linalg.norm(x - 1j * np.ones(2), 1)
sol = minimize(fun, x0=np.ones(2) + 0j)
输出为
>>> sol
fun: 2.0
hess_inv: array([[ 9.99997339e-01, -2.66135332e-06],
[-2.66135332e-06, 9.99997339e-01]])
jac: array([0., 0.])
message: 'Optimization terminated successfully.'
nfev: 24
nit: 5
njev: 6
status: 0
success: True
x: array([6.18479071e-09+0.j, 6.18479071e-09+0.j])
也不是很好。我尝试为minimize
指定所有可能的方法(根据需要提供Jacobian和Hessian),但是没有一个得到正确的结果。其中大多数导致ComplexWarning: Casting complex values to real discards the imaginary part
,表明它们不能正确处理复数。
使用scipy.optimize
是否可以实现这一点?
如果是这样的话,如果有人能告诉我我做错了什么,我将非常感激。
如果没有,你是否有其他的优化工具(Python)的建议?
2条答案
按热度按时间deikduxw1#
SciPy的最小化方法只适用于真实的参数。但在复数空间Cn上的最小化相当于在R2n上的最小化,复数代数从未进入考虑范围。因此,添加两个 Package 器用于从Cn到R2n和从R2n到Cn的转换,您可以对复数进行优化。
你提到了雅可比行列式和海森行列式......但最小化只对实值函数有意义,而实值函数对于复变量是永远不可微的。无论如何,雅可比行列式和海森行列式都必须在R2n上计算,将实部和虚部视为单独的变量。
hsvhsicv2#
我需要在真实的域上最小化复值模型函数对复值参数的偏离。
一个玩具例子:
定义f(x,a,B):ab =复合物(a,b);返回np.exp(x*ab)
假设我有数据DATA,x = np·arange(N),注意x是真实的。
我所做的是这样的:
定义辅助对象(x,a,B):返回绝对值(f(x,a,b)- DATA[x])
然后我可以使用curve_fit():
curve_fit(辅助对象,np.范围(N),np.零(N),p0 = [1,0])
发生的事情是这样的:通过从模型函数中减去数据,新的“理想”输出是全零,为了使curve_fit()起作用,它可以(必须)是真实的。复参数ab = a + jb已经被分解为实部和虚部。helper()函数返回模型和数据之间的差的绝对值。
一个关键的问题是curve_fit()只计算你给予它的x值,否则DATA[x]会失败。
请注意,通过使用abs(),我实现了L1拟合(或多或少)。我们也可以使用abs()**2来获得L2拟合......但为什么要使用L1或L2是另一天的主题。
你可能会担心,“假设x[]不是整数(而是真实的)?”这正是我的代码所要求的。嗯,这是可行的,只需将它们放入数组中,并对其进行索引。可能有一些聪明的黑客使用字典来解决这个问题。
很抱歉代码格式化;我还没弄清楚价格.