mirror of
https://gitlab.com/libeigen/eigen.git
synced 2026-04-10 11:34:33 +08:00
bug #1268: detect faillure in LDLT and report them through info()
This commit is contained in:
@@ -154,6 +154,7 @@ template<typename MatrixType> void cholesky(const MatrixType& m)
|
||||
SquareMatrixType symmLo = symm.template triangularView<Lower>();
|
||||
|
||||
LDLT<SquareMatrixType,Lower> ldltlo(symmLo);
|
||||
VERIFY(ldltlo.info()==Success);
|
||||
VERIFY_IS_APPROX(symm, ldltlo.reconstructedMatrix());
|
||||
vecX = ldltlo.solve(vecB);
|
||||
VERIFY_IS_APPROX(symm * vecX, vecB);
|
||||
@@ -170,6 +171,7 @@ template<typename MatrixType> void cholesky(const MatrixType& m)
|
||||
|
||||
|
||||
LDLT<SquareMatrixType,Upper> ldltup(symmUp);
|
||||
VERIFY(ldltup.info()==Success);
|
||||
VERIFY_IS_APPROX(symm, ldltup.reconstructedMatrix());
|
||||
vecX = ldltup.solve(vecB);
|
||||
VERIFY_IS_APPROX(symm * vecX, vecB);
|
||||
@@ -331,6 +333,7 @@ template<typename MatrixType> void cholesky_cplx(const MatrixType& m)
|
||||
RealMatrixType symmLo = symm.template triangularView<Lower>();
|
||||
|
||||
LDLT<RealMatrixType,Lower> ldltlo(symmLo);
|
||||
VERIFY(ldltlo.info()==Success);
|
||||
VERIFY_IS_APPROX(symm, ldltlo.reconstructedMatrix());
|
||||
vecX = ldltlo.solve(vecB);
|
||||
VERIFY_IS_APPROX(symm * vecX, vecB);
|
||||
@@ -367,35 +370,88 @@ template<typename MatrixType> void cholesky_definiteness(const MatrixType& m)
|
||||
{
|
||||
mat << 1, 0, 0, -1;
|
||||
ldlt.compute(mat);
|
||||
VERIFY(ldlt.info()==Success);
|
||||
VERIFY(!ldlt.isNegative());
|
||||
VERIFY(!ldlt.isPositive());
|
||||
}
|
||||
{
|
||||
mat << 1, 2, 2, 1;
|
||||
ldlt.compute(mat);
|
||||
VERIFY(ldlt.info()==Success);
|
||||
VERIFY(!ldlt.isNegative());
|
||||
VERIFY(!ldlt.isPositive());
|
||||
}
|
||||
{
|
||||
mat << 0, 0, 0, 0;
|
||||
ldlt.compute(mat);
|
||||
VERIFY(ldlt.info()==Success);
|
||||
VERIFY(ldlt.isNegative());
|
||||
VERIFY(ldlt.isPositive());
|
||||
}
|
||||
{
|
||||
mat << 0, 0, 0, 1;
|
||||
ldlt.compute(mat);
|
||||
VERIFY(ldlt.info()==Success);
|
||||
VERIFY(!ldlt.isNegative());
|
||||
VERIFY(ldlt.isPositive());
|
||||
}
|
||||
{
|
||||
mat << -1, 0, 0, 0;
|
||||
ldlt.compute(mat);
|
||||
VERIFY(ldlt.info()==Success);
|
||||
VERIFY(ldlt.isNegative());
|
||||
VERIFY(!ldlt.isPositive());
|
||||
}
|
||||
}
|
||||
|
||||
template<typename>
|
||||
void cholesky_faillure_cases()
|
||||
{
|
||||
MatrixXd mat;
|
||||
LDLT<MatrixXd> ldlt;
|
||||
|
||||
{
|
||||
mat.resize(2,2);
|
||||
mat << 0, 1, 1, 0;
|
||||
ldlt.compute(mat);
|
||||
VERIFY_IS_NOT_APPROX(mat,ldlt.reconstructedMatrix());
|
||||
VERIFY(ldlt.info()==NumericalIssue);
|
||||
}
|
||||
{
|
||||
mat.resize(3,3);
|
||||
mat << -1, -3, 3,
|
||||
-3, -8.9999999999999999999, 1,
|
||||
3, 1, 0;
|
||||
ldlt.compute(mat);
|
||||
VERIFY(ldlt.info()==NumericalIssue);
|
||||
VERIFY_IS_NOT_APPROX(mat,ldlt.reconstructedMatrix());
|
||||
}
|
||||
{
|
||||
mat.resize(3,3);
|
||||
mat << 1, 2, 3,
|
||||
2, 4, 1,
|
||||
3, 1, 0;
|
||||
ldlt.compute(mat);
|
||||
VERIFY(ldlt.info()==NumericalIssue);
|
||||
VERIFY_IS_NOT_APPROX(mat,ldlt.reconstructedMatrix());
|
||||
}
|
||||
|
||||
{
|
||||
mat.resize(8,8);
|
||||
mat << 0.1, 0, -0.1, 0, 0, 0, 1, 0,
|
||||
0, 4.24667, 0, 2.00333, 0, 0, 0, 0,
|
||||
-0.1, 0, 0.2, 0, -0.1, 0, 0, 0,
|
||||
0, 2.00333, 0, 8.49333, 0, 2.00333, 0, 0,
|
||||
0, 0, -0.1, 0, 0.1, 0, 0, 1,
|
||||
0, 0, 0, 2.00333, 0, 4.24667, 0, 0,
|
||||
1, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 1, 0, 0, 0;
|
||||
ldlt.compute(mat);
|
||||
VERIFY(ldlt.info()==NumericalIssue);
|
||||
VERIFY_IS_NOT_APPROX(mat,ldlt.reconstructedMatrix());
|
||||
}
|
||||
}
|
||||
|
||||
template<typename MatrixType> void cholesky_verify_assert()
|
||||
{
|
||||
MatrixType tmp;
|
||||
@@ -445,5 +501,7 @@ void test_cholesky()
|
||||
CALL_SUBTEST_9( LLT<MatrixXf>(10) );
|
||||
CALL_SUBTEST_9( LDLT<MatrixXf>(10) );
|
||||
|
||||
CALL_SUBTEST_2( cholesky_faillure_cases<void>() );
|
||||
|
||||
TEST_SET_BUT_UNUSED_VARIABLE(nb_temporaries)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user