14 #include <gtsam/linear/IterativeSolver.h>
26 typedef boost::shared_ptr<ConjugateGradientParameters> shared_ptr;
40 : minIterations_(1), maxIterations_(500), reset_(501), epsilon_rel_(1e-3),
41 epsilon_abs_(1e-3), blas_kernel_(GTSAM) {}
43 ConjugateGradientParameters(
size_t minIterations,
size_t maxIterations,
size_t reset,
44 double epsilon_rel,
double epsilon_abs, BLASKernel blas)
45 : minIterations_(minIterations), maxIterations_(maxIterations), reset_(reset),
46 epsilon_rel_(epsilon_rel), epsilon_abs_(epsilon_abs), blas_kernel_(blas) {}
48 ConjugateGradientParameters(
const ConjugateGradientParameters &p)
49 : Base(p), minIterations_(p.minIterations_), maxIterations_(p.maxIterations_), reset_(p.reset_),
50 epsilon_rel_(p.epsilon_rel_), epsilon_abs_(p.epsilon_abs_), blas_kernel_(GTSAM) {}
53 inline size_t minIterations()
const {
return minIterations_; }
54 inline size_t maxIterations()
const {
return maxIterations_; }
55 inline size_t reset()
const {
return reset_; }
56 inline double epsilon()
const {
return epsilon_rel_; }
57 inline double epsilon_rel()
const {
return epsilon_rel_; }
58 inline double epsilon_abs()
const {
return epsilon_abs_; }
60 inline size_t getMinIterations()
const {
return minIterations_; }
61 inline size_t getMaxIterations()
const {
return maxIterations_; }
62 inline size_t getReset()
const {
return reset_; }
63 inline double getEpsilon()
const {
return epsilon_rel_; }
64 inline double getEpsilon_rel()
const {
return epsilon_rel_; }
65 inline double getEpsilon_abs()
const {
return epsilon_abs_; }
67 inline void setMinIterations(
size_t value) { minIterations_ = value; }
68 inline void setMaxIterations(
size_t value) { maxIterations_ = value; }
69 inline void setReset(
size_t value) { reset_ = value; }
70 inline void setEpsilon(
double value) { epsilon_rel_ = value; }
71 inline void setEpsilon_rel(
double value) { epsilon_rel_ = value; }
72 inline void setEpsilon_abs(
double value) { epsilon_abs_ = value; }
76 virtual void print(std::ostream &os)
const;
78 static std::string blasTranslator(
const BLASKernel k) ;
79 static BLASKernel blasTranslator(
const std::string &s) ;
89 template <
class S,
class V>
90 V preconditionedConjugateGradient(
const S &system,
const V &initial,
const ConjugateGradientParameters ¶meters) {
92 V estimate, residual, direction, q1, q2;
93 estimate = residual = direction = q1 = q2 = initial;
95 system.residual(estimate, q1);
96 system.leftPrecondition(q1, residual);
97 system.rightPrecondition(residual, direction);
99 double currentGamma = system.dot(residual, residual), prevGamma, alpha, beta;
101 const size_t iMaxIterations = parameters.maxIterations(),
102 iMinIterations = parameters.minIterations(),
103 iReset = parameters.reset() ;
104 const double threshold =
std::max(parameters.epsilon_abs(),
105 parameters.epsilon() * parameters.epsilon() * currentGamma);
107 if (parameters.verbosity() >= ConjugateGradientParameters::COMPLEXITY )
108 std::cout <<
"[PCG] epsilon = " << parameters.epsilon()
109 <<
", max = " << parameters.maxIterations()
110 <<
", reset = " << parameters.reset()
111 <<
", ||r0||^2 = " << currentGamma
112 <<
", threshold = " << threshold << std::endl;
115 for ( k = 1 ; k <= iMaxIterations && (currentGamma > threshold || k <= iMinIterations) ; k++ ) {
117 if ( k % iReset == 0 ) {
118 system.residual(estimate, q1);
119 system.leftPrecondition(q1, residual);
120 system.rightPrecondition(residual, direction);
121 currentGamma = system.dot(residual, residual);
123 system.multiply(direction, q1);
124 alpha = currentGamma / system.dot(direction, q1);
125 system.axpy(alpha, direction, estimate);
126 system.leftPrecondition(q1, q2);
127 system.axpy(-alpha, q2, residual);
128 prevGamma = currentGamma;
129 currentGamma = system.dot(residual, residual);
130 beta = currentGamma / prevGamma;
131 system.rightPrecondition(residual, q1);
132 system.scal(beta, direction);
133 system.axpy(1.0, q1, direction);
135 if (parameters.verbosity() >= ConjugateGradientParameters::ERROR )
136 std::cout <<
"[PCG] k = " << k
137 <<
", alpha = " << alpha
138 <<
", beta = " << beta
139 <<
", ||r||^2 = " << currentGamma
142 if (parameters.verbosity() >= ConjugateGradientParameters::COMPLEXITY )
143 std::cout <<
"[PCG] iterations = " << k
144 <<
", ||r||^2 = " << currentGamma
size_t reset_
number of iterations before reset
Definition: ConjugateGradientSolver.h:30
double epsilon_rel_
threshold for relative error decrease
Definition: ConjugateGradientSolver.h:31
parameters for iterative linear solvers
Definition: IterativeSolver.h:38
size_t minIterations_
minimum number of cg iterations
Definition: ConjugateGradientSolver.h:28
void print(const Matrix &A, const string &s, ostream &stream)
print a matrix
Definition: Matrix.cpp:183
double max(const Vector &a)
Return the max element of a vector.
Definition: Vector.cpp:238
BLASKernel
Definition: ConjugateGradientSolver.h:35
double epsilon_abs_
threshold for absolute error decrease
Definition: ConjugateGradientSolver.h:32
parameters for the conjugate gradient method
Definition: ConjugateGradientSolver.h:22
size_t maxIterations_
maximum number of cg iterations
Definition: ConjugateGradientSolver.h:29