Pandas 用奇异值分解法求解欠定稀疏矩阵 问题
我有一组等式,变量用小写变量表示,常量用大写变量表示Pandas 用奇异值分解法求解欠定稀疏矩阵 问题,pandas,sparse-matrix,linear-algebra,svd,Pandas,Sparse Matrix,Linear Algebra,Svd,我有一组等式,变量用小写变量表示,常量用大写变量表示 A = a + b B = c + d C = a + b + c + d + e 我在一个包含两列的数据框架中获得了关于这些方程结构的信息:常量和变量 例如 然后使用NetworkX将其转换为稀疏CSC矩阵 table = nx.bipartite.biadjacency_matrix(nx.from_pandas_dataframe(df,'Constants','Variables') ,df.Constants.un
A = a + b
B = c + d
C = a + b + c + d + e
我在一个包含两列的数据框架中获得了关于这些方程结构的信息:常量和变量
例如
然后使用NetworkX将其转换为稀疏CSC矩阵
table = nx.bipartite.biadjacency_matrix(nx.from_pandas_dataframe(df,'Constants','Variables')
,df.Constants.unique(),df.Variables.unique(),format='csc')
当转换为密集矩阵时,表如下所示
矩阵([[1,1,0,0,0,0],[0,0,1,1,0],[1,1,1,1]],dtype=int64)
我想从这里找到哪些变量是可解的(在这个例子中,只有e是可解的),对于每个可解变量,它的值依赖于哪些常数(在这种情况下,由于e=C-B-A,它依赖于A、B和C)
试图解决问题
我首先尝试使用rref来求解可解变量。我使用了符号库sympy和函数sympy.Matrix.rref,这正是我想要的,因为任何可解变量都有自己的行,几乎所有的0和1,我可以逐行检查
然而,这种溶液并不稳定。首先,它非常慢,并且没有利用我的数据集可能非常稀疏这一事实。此外,rref在浮点运算方面做得不太好。因此,我决定转向另一种方法,该方法的动机是,建议使用svd
方便的是,scipy.sparse库中有一个svd函数,即scipy.sparse.linalg.svds。然而,鉴于我缺乏线性代数背景,我不理解在我的表上运行此函数所输出的结果,或者如何使用这些结果来获得我想要的结果
问题的进一步细节
这是我第一次发布问题,如果这不完全符合指导原则,我深表歉意。请留下建设性的批评,但要温柔 您正在求解的系统具有以下形式
[ 1 1 0 0 0 ] [a] [A]
[ 0 0 1 1 0 ] [b] = [B]
[ 1 1 1 1 1 ] [c] [C]
[d]
[e]
i、 五个变量的三个方程a、b、c、d、e
。正如你问题中的答案所提到的,你可以用Numpy直接提供的功能来解决这种不确定的系统
由于M
具有线性独立的行,因此在这种情况下,PSUDOVERSE具有M.pinv(M)=I
的属性,其中I
表示单位矩阵(在这种情况下为3x3)。因此,在形式上,我们可以将解决方案写成:
v = pinv(M) . b
其中,v
是五组分溶液向量,b
表示右侧三组分向量[A,b,C]
。然而,该解决方案不是唯一的,因为可以从所谓的内核或矩阵M
(即,向量w
,其中M.w=0
)中添加向量,并且它仍然是一个解决方案:
M.(v + w) = M.v + M.w = b + 0 = b
因此,唯一存在唯一解决方案的变量是M
零空间中所有可能向量的对应分量为零的变量。换句话说,如果将零空间的基组合成一个矩阵(每列一个基向量),那么“可解变量”将对应于该矩阵的零行(列的任何线性组合的相应分量也将为零)
让我们将此应用于您的特定示例:
import numpy as np
from numpy.linalg import pinv
M = [
[1, 1, 0, 0, 0],
[0, 0, 1, 1, 0],
[1, 1, 1, 1, 1]
]
print(pinv(M))
[[ 5.00000000e-01 -2.01966890e-16 1.54302378e-16]
[ 5.00000000e-01 1.48779676e-16 -2.10806254e-16]
[-8.76351626e-17 5.00000000e-01 8.66819360e-17]
[-2.60659800e-17 5.00000000e-01 3.43000417e-17]
[-1.00000000e+00 -1.00000000e+00 1.00000000e+00]]
从这个伪逆中,我们看到变量e
(最后一行)确实可以表示为-A-B+C
。然而,它也“预测”了a=a/2
和b=a/2
。为了消除这些非唯一解(例如,同样有效的还有a=a
和b=0
),让我们计算借用SciPy函数的空空间:
这个函数已经返回组装成矩阵的零空间的基(每列一个向量),我们可以看到,在合理的精度范围内,唯一的零行实际上只是对应于变量e
的最后一行
编辑:
对于方程组
A = a + b, B = b + c, C = a + c
相应的矩阵M
为
[ 1 1 0 ]
[ 0 1 1 ]
[ 1 0 1 ]
这里我们看到矩阵实际上是平方的,并且是可逆的(行列式是2
)。因此,伪逆与“正常”逆重合:
它对应于解决方案
a=(a-B+C)/2,…
。因为M
是可逆的,所以它的内核/null空间是空的,这就是为什么cookbook函数只返回[]
。为了了解这一点,让我们使用内核的定义-它由所有非零向量x
构成,这样M.x=0
。然而,由于存在M^{-1}
,因此x
被给出为x=M^{-1}。0=0
这是一个矛盾。形式上,这意味着找到的解决方案是唯一的(或者所有变量都是“可解的”)。要基于ewcz的答案,可以使用numpy.linalg.svd
计算零空间和伪逆。请参阅以下链接:
谢谢您的详细回复!我喜欢使用nullspace,但我有两个问题。首先,您知道在nullspace体中是否可以使用稀疏svd函数吗?我试图把它隐藏起来,但我没能弄明白。食谱中的零空间函数似乎也不适用于方程A=A+b,b=b+c,c=A+c的情况。我不想成为这里的吸血鬼帮手,但我真的不明白nullspace是怎么工作的。@RushabhMehta,我的荣幸!我没有详细研究稀疏版本,但只要它提供左/右奇异向量和
A = a + b, B = b + c, C = a + c
[ 1 1 0 ]
[ 0 1 1 ]
[ 1 0 1 ]
[[ 0.5 -0.5 0.5]
[ 0.5 0.5 -0.5]
[-0.5 0.5 0.5]]