使用python约束最小二乘拟合

时间:2013-08-08 19:06:00

标签: python-3.x

任何人都可以帮我编写python脚本吗?问题如下所述。

我需要执行一些线性方程的等式约束线性最小二乘拟合。对于特定的线性方程,矩阵方程看起来像[Y] {nX1} = [X] {nXm} [P] _ {mX1},其中Y和P是向量,X是矩阵n和m是矩阵的维数。此外,P上存在等式约束,即Sum(P(i))= 0.0。有谁知道如何解决这个问题? python的哪个函数适合这个?我在scipy.optimize.fmin_slsqp()函数中看到了很少的讨论,但是使用这个函数并不是很简单。

然而,我可以通过使用numpy轻松地完成上述问题的无约束最小二乘拟合。这是一个小脚本。

import numpy as np
from numpy import matrix
from numpy import arange,array,ones,linalg
x = np.random.randn(500,3)
A=matrix([[3.0, 4.0, -7.0],[4.0, -5.0, 1.0],[3.0, 2.0, -5.0]])
y=A*x.T
w=linalg.lstsq(x,y.T)[0]
print w.T

这里我生成了一个随机向量x,然后通过A和x.T的矩阵乘法生成向量y。然后我使用x和y向量并评估矩阵A的元素。上面的脚本完美地再现了矩阵A.这使我对lsf的工作充满信心。然而,它只是最小的方形拟合。没有限制。

另一件事是,是否可以将受约束的lsf问题转换为无约束的lsf问题。如果是这样,那么我可以使用上面的脚本。拉格朗日乘数的方法是可能的选择之一。但是,我很难评估我的问题的乘数。这是因为,等式包含大量的变量。如果有

顺便说一下,MATLAB中约束lsf的相似函数是lsqlin。

我上周正在努力解决这个问题。在这方面请帮帮我。如果您有任何其他建议,那么这也很棒。

祝福

3 个答案:

答案 0 :(得分:1)

如果您的问题不是太大,您可以通过求解等效的线性系统来解决它。假设您以

的形式编写约束最小二乘问题
min 1/2 |Ax - b|^2
subject to  Bx = c,

在Euclidian规范中(StackOverflow不支持MathJax真的很糟糕!)1/2因为方便起见。通过求解线性系统可以等效地找到上述问题的解x(假设有一个)

[ I   A  0   ] [ r ]   [ b ]
[ A.T 0  B.T ] [ x ] = [ 0 ]
[ 0   B  0   ] [ y ]   [ c ]

其中零块具有适当的大小,.T表示转置​​,I是适当大小的单位矩阵。您正在寻找解决方案向量的中间部分。请注意,上面的矩阵是对称的,但它是不确定的,所以如果你没有专门的东西,你将不得不使用LU分解来解决系统(没关系,但你可以节省大约一半的工作。)你可以'使用Cholesky。

如果您的问题很大,您也可以使用MINRES来解决上述系统,而无需实际组装或分解它。您只需要提供一个用此矩阵计算产品的LinearOperator

我还发现:https://gist.github.com/fabianp/915461(但尚未经过测试)。

答案 1 :(得分:0)

您可以尝试Golub和van Loan在'矩阵计算'中提到的'权重方法',这是一种只需要设计矩阵的近似方法。

答案 2 :(得分:0)

对于稠密矩阵,受等式约束的线性最小二乘拟合目前在Python中可用(Scipy 1.5),可直接调用相关的LAPACK例程scipy.linalg.lapack.dgglse。 DGGLSE的LAPACK文档为here

例如,解决问题的方法

min ||A @ x - b||
subject to  C @ x = d

可以使用Python代码获得

from scipy.linalg import lapack

# Define the matrices as usual, then
x = lapack.dgglse(A, C, b, d)[3]