介紹如何求解線性系統,計算幾種分解,比如LU,QR,SVD等。
基本的線性求解
問題:假設有一個系統方程寫成如下矩陣的形式
Ax=b
其中A,b是矩陣,b也可以是向量,當想要求解x時,可以選擇多種分解方式,取決於矩陣A的形式以及考慮的速度和精度,下面是一個簡單的例子。
#include <iostream>
#include <Eigen/Dense>
using namespace std;
using namespace Eigen;
int main()
{
Matrix3f A;
Vector3f b;
A << 1,2,3, 4,5,6, 7,8,10;
b << 3, 3, 4;
cout << "Here is the matrix A:\n" << A << endl;
cout << "Here is the vector b:\n" << b << endl;
Vector3f x = A.colPivHouseholderQr().solve(b);
cout << "The solution is:\n" << x << endl;
}
求解爲:
Here is the matrix A:
1 2 3
4 5 6
7 8 10
Here is the vector b:
3
3
4
The solution is:
-2
1
1
例子中colPivHouseholderQr()方法返回一個類ColPivHouseholderQR的對象,因此那句話也可以寫成
ColPivHouseholderQR<Matrix3f> dec(A);
Vector3f x = dec.solve(b);
這裏ColPivHouseholderQR是QR分解的意思,適用於各種矩陣並且速度夠快,下面是幾種分解的對比
Decomposition | Method | Requirements on the matrix | Speed (small-to-medium) | Speed (large) | Accuracy |
---|---|---|---|---|---|
PartialPivLU | partialPivLu() | Invertible | ++ | ++ | + |
FullPivLU | fullPivLu() | None | - | - - | +++ |
HouseholderQR | householderQr() | None | ++ | ++ | + |
ColPivHouseholderQR | colPivHouseholderQr() | None | ++ | - | +++ |
FullPivHouseholderQR | fullPivHouseholderQr() | None | - | - - | +++ |
LLT | lt() | Positive | definite | +++ | +++ |
LDLT | ldlt() | Positive or negative semidefinite | +++ | + | ++ |
JacobiSVD | jacobiSvd() | None | - - | - - - | +++ |
以上分解都提供了solve()方法。比如當矩陣是正定的時候,表中說明LLT和LDLT是不錯的選擇。