Hi, Sameer, thanks a lot for your attention and help. I tried this patch, it still failed the convergence after the first iteration.
1) For our testing problem, this is printed information using the patch you provided (the optimization stops after the first iteration):
0: f: 5.221393e+05 d: 0.00e+00 g: 5.24e+05 h: 0.00e+00 s: 0.00e+00 e: 0 it: 9.41e-03 tt: 9.49e-03
WARNING: Logging before InitGoogleLogging() is written to STDERR
W1229 11:02:50.069532 20645 line_search.cc:772] Line search failed: Wolfe zoom phase failed to find a point satisfying strong Wolfe conditions within specified max_num_iterations: 20, (num iterations taken for bracketing: 1).
Here is the initial cost and final cost:
summary.initial_cost = 522139.339699653 summary.final_cost = 522139.339699653
If we switched to the fix we came up with (lu_lhs.setThreshold( 0.0 ).solve( rhs );), here are the printed information
0: f: 5.221393e+05 d: 0.00e+00 g: 5.24e+05 h: 0.00e+00 s: 0.00e+00 e: 0 it: 9.85e-03 tt: 9.93e-03
1: f: 5.151351e+05 d: 7.00e+03 g: 3.86e+05 h: 6.91e-02 s: 1.21e-07 e: 2 it: 7.56e-03 tt: 1.76e-02
...
760: f: 2.995621e-01 d: 6.87e-11 g: 6.53e-02 h: 8.57e-05 s: 1.00e+00 e: 1 it: 4.66e-03 tt: 3.39e+00
761: f: 2.995621e-01 d: 3.56e-11 g: 4.51e-02 h: 2.51e-04 s: 1.00e+00 e: 1 it: 3.33e-03 tt: 3.39e+00
Here is the initial cost and final cost:
summary.initial_cost = 522139.339699653 summary.final_cost = 0.299562082
2) Here is one unit test I created to check the behavior of fullPivLu on a rank deficient matrix (this matrix is actually from the first iteration of our testing problem in FindInterpolatingPolynomial):
ceres::Matrix lhs = ceres::Matrix::Zero( 4, 4 );
ceres::Vector rhs = ceres::Vector::Zero( 4 );
lhs << 0, 0, 0, 1,
0, 0, 1, 0,
6.94062e-18, 3.63858e-12, 1.90751e-06, 1,
1.09157e-11, 3.81501e-06, 1, 0;
rhs << 522139, -3.25765e+11, 1.81769e+06, -4.06082e+10;
auto result1 = lhs.fullPivLu().solve( rhs );
Eigen::FullPivLU<ceres::Matrix> lu_lhs( lhs );
auto result2 = lu_lhs.setThreshold( 0.0 ).solve( rhs );
std::cout << "result1: " << result1 << std::endl;
std::cout << "result2: " << result2 << std::endl;
We use Eigen 3.3.1, the printed answer on my machine is the following:
result1:
0
7.4746e+16
-3.25765e+11
522139
result2:
-4.74021e+23
1.43104e+18
-3.25765e+11
522139
result1 will fail the convergence, result2 can make the optimization continue.
3) I also have one question about the patch you provided, for a 4x4 matrix lhs, if lhs has rank 3, it will return a 3x1 vector, right? But it is supposed to return a 4x1 vector, will this cause any problem?