在C++中更高效快速地求解矩阵的逆(大型和小型)

11
编辑。自问此问题以来,我已经在解决层析成像中的线性方程组问题上获得了博士学位。由于这个问题仍然受到很多关注,我想强调来自 @sellibitze 答案中的第一句话:没有简单的答案。它高度取决于矩阵的性质,几乎总是不希望反转矩阵。

现在,针对这位认为这可以轻松回答的无辜之人的原始问题...


在搜索矩阵求逆算法时,我发现有几种(和意见!)关于如何在代码中执行此操作的方式。我想知道哪种方法最快或性能最佳,并试图找到答案,但我什么都没找到。

我知道对于某些情况,可以计算一个伪逆(使用SVD、Cholevsky等),我实际上在我的代码中使用了其中一些,并且我知道有时候根本不存在逆矩阵等。可以轻松地找到一个特定问题的具体答案,但是对于这个大(巨大!)问题——矩阵求逆,很难得出一般性的直觉。

所以我的问题是:

针对小矩阵,哪种方法在性能方面最佳?精度呢?对于大矩阵呢?

我个人的情况是一个6x6(编辑:对称)矩阵需要被反转数千次(是的,是的,采用不同的值),我需要高精度,但当然速度也很重要。

请注意,我在寻找代码,我将自己编写适合我情况的任何答案,但我认为这是许多程序员想知道的问题。


1
你为什么想要翻转一个矩阵? - Agentlien
@Agentlien 我(认为我)需要求一个矩阵的逆,因为我正在使用牛顿-拉弗森算法最小化一个6个元素向量的梯度,其导数是Hessian矩阵,一个6x6的矩阵。我不需要解决Ax=B类型的方程。 - Ander Biguri
1
@AnderBiguri 关于你正在解决的问题。我在解决类似问题时遇到了一篇不错的文章(http://rkb.home.cern.ch/rkb/AN16pp/node147.html),并成功地避免了矩阵求逆的问题。这个方法可能或者不适用于你的情况,但我想分享这个链接。 - Angew is no longer proud of SO
1
@Agentlien:你不需要求逆矩阵。你可能正在尝试计算inv(A)*some_vector,但没有必要显式地计算inv(A)。你可以通过分解A并进行一些前向/后向替换来计算上述乘积。 - sellibitze
1
@AnderBiguri:抱歉,我以为我已经回答了你的问题。但是我发现我错把另一个人(Agentlien)称呼了。 - sellibitze
显示剩余6条评论
1个回答

5

没有简单的答案。请确保您已经阅读并理解了this文章。

对于2x2矩阵,计算逆可以使用涉及行列式的简单公式完成。但对于更大的矩阵,我更喜欢因子分解,例如旋转LU分解。如果您关心性能并处理大型稀疏矩阵,则迭代求解器可能是合适的选择。或者您可以尝试MUMPS(多前端大规模并行求解器)并测量性能。迭代求解器的问题在于其收敛速度严重取决于逆问题的条件以及是否找到良好的预处理器。

也许您应该从Eigen库开始,首先尝试旋转LU分解。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接