core/vnl/algo/vnl_cholesky.h
Go to the documentation of this file.
00001 // This is core/vnl/algo/vnl_cholesky.h
00002 #ifndef vnl_cholesky_h_
00003 #define vnl_cholesky_h_
00004 #ifdef VCL_NEEDS_PRAGMA_INTERFACE
00005 #pragma interface
00006 #endif
00007 //:
00008 // \file
00009 // \brief Decomposition of symmetric matrix
00010 // \author Andrew W. Fitzgibbon, Oxford RRG
00011 // \date   08 Dec 96
00012 //
00013 // \verbatim
00014 //  Modifications
00015 //   Peter Vanroose, Leuven, Apr 1998: added L() (return decomposition matrix)
00016 //   dac (Manchester) 26/03/2001: tidied up documentation
00017 //   Feb.2002 - Peter Vanroose - brief doxygen comment placed on single line
00018 // \endverbatim
00019 
00020 #include <vnl/vnl_vector.h>
00021 #include <vnl/vnl_matrix.h>
00022 
00023 //: Decomposition of symmetric matrix.
00024 //  A class to hold the Cholesky decomposition of a symmetric matrix and
00025 //  use that to solve linear systems, compute determinants and inverses.
00026 //  The cholesky decomposition decomposes symmetric A = L*L.transpose()
00027 //  where L is lower triangular
00028 //
00029 //  To check that the decomposition can be used safely for solving a linear
00030 //  equation it is wise to construct with mode==estimate_condition and
00031 //  check that rcond()>sqrt(machine precision).  If this is not the case
00032 //  it might be a good idea to use vnl_svd instead.
00033 class vnl_cholesky
00034 {
00035  public:
00036   //: Modes of computation.  See constructor for details.
00037   enum Operation {
00038     quiet,
00039     verbose,
00040     estimate_condition
00041   };
00042 
00043   //: Make cholesky decomposition of M optionally computing the reciprocal condition number.
00044   vnl_cholesky(vnl_matrix<double> const& M, Operation mode = verbose);
00045  ~vnl_cholesky() {}
00046 
00047   //: Solve LS problem M x = b
00048   vnl_vector<double> solve(vnl_vector<double> const& b) const;
00049 
00050   //: Solve LS problem M x = b
00051   void solve(vnl_vector<double> const& b, vnl_vector<double>* x) const;
00052 
00053   //: Compute determinant
00054   double determinant() const;
00055 
00056   //   Compute inverse.  Not efficient.
00057   // It's broken, I don't have time to fix it.
00058   // Mail awf@robots if you need it and I'll tell you as much as I can
00059   // to fix it.
00060   vnl_matrix<double> inverse() const;
00061 
00062   //: Return lower-triangular factor.
00063   vnl_matrix<double> lower_triangle() const;
00064 
00065   //: Return upper-triangular factor.
00066   vnl_matrix<double> upper_triangle() const;
00067 
00068   //: Return the decomposition matrix
00069   vnl_matrix<double> const& L_badly_named_method() const { return A_; }
00070 
00071   //: A Success/failure flag
00072   int rank_deficiency() const { return num_dims_rank_def_; }
00073 
00074   //: Return reciprocal condition number (smallest/largest singular values).
00075   // As long as rcond()>sqrt(precision) the decomposition can be used for
00076   // solving equations safely.
00077   // Not calculated unless Operation mode at construction was estimate_condition.
00078   double rcond() const { return rcond_; }
00079 
00080   //: Return computed nullvector.
00081   // Not calculated unless Operation mode at construction was estimate_condition.
00082   vnl_vector<double>      & nullvector()       { return nullvector_; }
00083   vnl_vector<double> const& nullvector() const { return nullvector_; }
00084 
00085  protected:
00086   // Data Members--------------------------------------------------------------
00087   vnl_matrix<double> A_;
00088   double rcond_;
00089   long num_dims_rank_def_;
00090   vnl_vector<double> nullvector_;
00091 
00092  private:
00093   //: Copy constructor - privatised to avoid it being used
00094   vnl_cholesky(vnl_cholesky const & that);
00095   //: Assignment operator - privatised to avoid it being used
00096   vnl_cholesky& operator=(vnl_cholesky const & that);
00097 };
00098 
00099 #endif // vnl_cholesky_h_