Ich versuche, Eigen3 zu bekommen, um ein lineares System A * X = B
mit einer In-Place-Cholesky-Zerlegung zu lösen. Ich kann es mir nicht leisten, irgendwelche Provisorien der Größe A
auf den Stapel zu schieben, aber ich bin frei, A
dabei zu zerstören. LeiderEigen LDLT Cholesky-Zerlegung an Ort und Stelle
,
A.llt().solveInPlace(B);
steht außer Frage, da A.llt()
implizit eine temporäre Matrix der Größe von A
auf den Stapel schiebt. Für den LLT
Fall konnte ich Zugriff auf die notwendige Funktionalität erhalten wie so:
// solve A * X = B in-place for positive-definite A
template <typename AType, typename BType>
void AllInPlaceSolve(AType& A, BType& B)
{
typedef Eigen::internal::LLT_Traits<AType, Eigen::Upper> TraitsType;
TraitsType::inplace_decomposition(A);
TraitsType::getL(A).solveInPlace(B);
TraitsType::getU(A).solveInPlace(B);
}
Dies funktioniert gut, aber ich bin besorgt, dass:
- Meine Matrizen
A
könnten nur positiv semidefinit sein, in denen Fall Zersetzung ein LDLT erforderlich - die
LLT
Zersetzung berechnetsqrt()
unnötig für die Lösung des Systems
Ich konnte keine Möglichkeit finden, die LDLT-Funktionalität von Eigen ähnlich dem obigen Code einzubinden, da der Code sehr unterschiedlich strukturiert ist.
Meine Frage ist also: Gibt es eine Möglichkeit, Eigen3 zu verwenden, um ein lineares System zu lösen, das LDLT-Zerlegungen verwendet und keinen Platz mehr für die Diagonalmatrix D
verwendet?
Leider muss ich wirklich mein eigenes Gedächtnis verwenden, also funktioniert keiner von beiden. Ich denke, was ich brauche, ist in 'internal :: ldlt_inplace :: unblocked()', aber es ist weniger offensichtlich für die Einrichtung als für den LLT-Fall. –
Stefan
Für den Fall, dass ich 'deblocked()' Setup bekommen kann, sind unsere Matrizen 'A' Zeilenmajor, aber da' A' symmetrisch ist, sollte ich 'A.transpose()' verwenden können, nein? – Stefan
Wenn die Matrix vollständig ist, dann, ja, können Sie eine Zeile-major oberen dreieckigen Teil als eine Spalte-Major unteren dreieckigen sehen. Sie müssen nur eine PermutationMatrix zuweisen, um sie an 'internal :: ldlt_inplace :: unblocked() 'zu übergeben. Das Hauptproblem ist, dass Sie den Lösungsschritt neu schreiben müssen. –
ggael