为了账号安全,请及时绑定邮箱和手机立即绑定

Scipy LDL分解返回意外结果

Scipy LDL分解返回意外结果

ibeautiful 2022-07-26 16:31:49
我生成了一个随机的 5*5 矩阵x,如下所示:>>> x = np.random.randn(5,5)并使用如下分解对其进行scipy.linalg.ldl分解:>>> l, d, p = la.ldl(x)使用l,d我p想返回 x。我以为我可以做到以下几点:>>> l[p,:] @ d @ l[p,:].transpose() - x但这并没有像我预期的那样给我零。谁能解释我哪里出错了?我的目标是获得下对角矩阵L,这样x = LDL^T就不需要行置换矩阵p,但我对 scipy 给出的输出感到非常困惑。
查看完整描述

1 回答

?
哈士奇WWW

TA贡献1799条经验 获得超6个赞

LDL 分解算法仅适用于 Hermitian/对称矩阵。您正在向它传递一个具有随机值的矩阵,该矩阵不太可能是对称的。此外,矩阵乘法应该在不将置换矩阵应用于下三角矩阵的情况下进行。


将非对称矩阵传递给 时scipy.linalg.ldl,仅引用矩阵的下三角部分或上三角部分,具体取决于lower关键字参数的值,默认为True。我们可以看到这样做的效果np.isclose():


>>> x = np.random.randn(5,5)

>>> l, d, p = la.ldl(x)

>>> np.isclose(l.dot(d).dot(l.T) - x, 0)

[[ True False False False False]

 [ True  True False False False]

 [ True  True  True False False]

 [ True  True  True  True False]

 [ True  True  True  True  True]]

在这里,我们看到矩阵的上三角部分被假定为对称的,因此算法返回的值在这种情况下是正确的。


下面,我们传递la.ldl一个实际的对称矩阵,得到预期的结果。


>>> x = np.array([[1, 2, 3],

                  [2, 4, 5],

                  [3, 5, 6]])

>>> l, d, p = la.ldl(x)

>>> print(np.isclose(l.dot(d).dot(l.T) - x, 0))

[[ True  True  True]

 [ True  True  True]

 [ True  True  True]]

如果您正在寻找一般的 LDL^T 分解,而没有 permutations,这将进一步减少矩阵的域。您的矩阵也需要是正定的。


下面是一个这样的矩阵示例:


>>> x = np.array([[2, -1, 0],

                  [-1, 3, -1],

                  [0, -1, 4]])

>>> l, d, p = la.ldl(x)

>>> l

array([[ 1. ,  0. ,  0. ],

       [-0.5,  1. ,  0. ],

       [ 0. , -0.4,  1. ]])

>>> d

array([[2. , 0. , 0. ],

       [0. , 2.5, 0. ],

       [0. , 0. , 3.6]])

>>> p

array([0, 1, 2], dtype=int64)

如您所见,排列p是[0, 1, 2],并且l已经是下三角形。


查看完整回答
反对 回复 2022-07-26
  • 1 回答
  • 0 关注
  • 104 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信