Expose lbfgs rank in solver.h

Change-Id: Ibc184b1a2f94a4057fa6569d539ca3a55d6d6098
diff --git a/include/ceres/solver.h b/include/ceres/solver.h
index 8aa91ee..88358bc 100644
--- a/include/ceres/solver.h
+++ b/include/ceres/solver.h
@@ -62,6 +62,7 @@
       line_search_direction_type = STEEPEST_DESCENT;
       line_search_type = ARMIJO;
       nonlinear_conjugate_gradient_type = FLETCHER_REEVES;
+      max_lbfgs_rank = 20;
       trust_region_strategy_type = LEVENBERG_MARQUARDT;
       dogleg_type = TRADITIONAL_DOGLEG;
       use_nonmonotonic_steps = false;
@@ -155,6 +156,17 @@
     LineSearchType line_search_type;
     NonlinearConjugateGradientType nonlinear_conjugate_gradient_type;
 
+    // The LBFGS hessian approximation is a low rank approximation to
+    // the inverse of the Hessian matrix. The rank of the
+    // approximation determines (linearly) the space and time
+    // complexity of using the approximation. Higher the rank, the
+    // better is the quality of the approximation.  For more details,
+    // please see:
+    //
+    // Nocedal, J. (1980). "Updating Quasi-Newton Matrices with
+    // Limited Storage". Mathematics of Computation 35 (151): 773–782.
+    int max_lbfgs_rank;
+
     TrustRegionStrategyType trust_region_strategy_type;
 
     // Type of dogleg strategy to use.
diff --git a/internal/ceres/line_search_minimizer.cc b/internal/ceres/line_search_minimizer.cc
index db0e814..a52d4de 100644
--- a/internal/ceres/line_search_minimizer.cc
+++ b/internal/ceres/line_search_minimizer.cc
@@ -47,7 +47,6 @@
 #include <limits>
 #include <string>
 #include <vector>
-#include <iostream>
 
 #include "Eigen/Dense"
 #include "ceres/array_utils.h"
@@ -194,7 +193,7 @@
 
   scoped_ptr<LBFGS> lbfgs;
   if (options_.line_search_direction_type == ceres::LBFGS) {
-    lbfgs.reset(new LBFGS(num_effective_parameters, 20));
+    lbfgs.reset(new LBFGS(num_effective_parameters, options_.max_lbfgs_rank));
   }
 
   while (true) {
@@ -224,7 +223,6 @@
       search_direction = -gradient;
       directional_derivative = -gradient_squared_norm;
     } else {
-
       if (lbfgs.get() != NULL) {
         lbfgs->Update(delta, gradient_change);
       }
diff --git a/internal/ceres/minimizer.h b/internal/ceres/minimizer.h
index 3d2bdee..2be3a3b 100644
--- a/internal/ceres/minimizer.h
+++ b/internal/ceres/minimizer.h
@@ -32,8 +32,9 @@
 #define CERES_INTERNAL_MINIMIZER_H_
 
 #include <vector>
-#include "ceres/solver.h"
+#include "ceres/internal/port.h"
 #include "ceres/iteration_callback.h"
+#include "ceres/solver.h"
 
 namespace ceres {
 namespace internal {
@@ -80,7 +81,9 @@
       min_trust_region_radius = options.min_trust_region_radius;
       line_search_direction_type = options.line_search_direction_type;
       line_search_type = options.line_search_type;
-      nonlinear_conjugate_gradient_type = options.nonlinear_conjugate_gradient_type;
+      nonlinear_conjugate_gradient_type =
+          options.nonlinear_conjugate_gradient_type;
+      max_lbfgs_rank = options.max_lbfgs_rank;
       evaluator = NULL;
       trust_region_strategy = NULL;
       jacobian = NULL;
@@ -114,7 +117,7 @@
     LineSearchDirectionType line_search_direction_type;
     LineSearchType line_search_type;
     NonlinearConjugateGradientType nonlinear_conjugate_gradient_type;
-
+    int max_lbfgs_rank;
 
     // List of callbacks that are executed by the Minimizer at the end
     // of each iteration.