Add a templated TypedPreconditioner class.

This sets the stage of preconditioners that can utilize
different kinds of matrix layouts, just like the LinearSolver
class hierarchy.

Change-Id: I3579cf344bcd2eeeecb1ae621cab02a3c9a0f920
diff --git a/internal/ceres/visibility_based_preconditioner.h b/internal/ceres/visibility_based_preconditioner.h
index 54a03e6..c58b1a7 100644
--- a/internal/ceres/visibility_based_preconditioner.h
+++ b/internal/ceres/visibility_based_preconditioner.h
@@ -123,7 +123,7 @@
 //   preconditioner.RightMultiply(x, y);
 //
 #ifndef CERES_NO_SUITESPARSE
-class VisibilityBasedPreconditioner : public Preconditioner {
+class VisibilityBasedPreconditioner : public BlockSparseMatrixPreconditioner {
  public:
   // Initialize the symbolic structure of the preconditioner. bs is
   // the block structure of the linear system to be solved. It is used
@@ -136,12 +136,13 @@
   virtual ~VisibilityBasedPreconditioner();
 
   // Preconditioner interface
-  virtual bool Update(const BlockSparseMatrix& A, const double* D);
   virtual void RightMultiply(const double* x, double* y) const;
   virtual int num_rows() const;
 
   friend class VisibilityBasedPreconditionerTest;
+
  private:
+  virtual bool UpdateImpl(const BlockSparseMatrix& A, const double* D);
   void ComputeClusterJacobiSparsity(const CompressedRowBlockStructure& bs);
   void ComputeClusterTridiagonalSparsity(const CompressedRowBlockStructure& bs);
   void InitStorage(const CompressedRowBlockStructure& bs);
@@ -203,7 +204,7 @@
 #else  // SuiteSparse
 // If SuiteSparse is not compiled in, the preconditioner is not
 // available.
-class VisibilityBasedPreconditioner : public Preconditioner {
+class VisibilityBasedPreconditioner : public BlockSparseMatrixPreconditioner {
  public:
   VisibilityBasedPreconditioner(const CompressedRowBlockStructure& bs,
                                 const Preconditioner::Options& options) {
@@ -215,7 +216,9 @@
   virtual void LeftMultiply(const double* x, double* y) const {}
   virtual int num_rows() const { return -1; }
   virtual int num_cols() const { return -1; }
-  bool Update(const BlockSparseMatrix& A, const double* D) {
+
+ private:
+  bool UpdateImpl(const BlockSparseMatrix& A, const double* D) {
     return false;
   }
 };