2012-03-23 11:38:57 +08:00
|
|
|
/* ----------------------------------------------------------------------------
|
|
|
|
|
|
|
|
|
|
* GTSAM Copyright 2010, Georgia Tech Research Corporation,
|
|
|
|
|
* Atlanta, Georgia 30332-0415
|
|
|
|
|
* All Rights Reserved
|
|
|
|
|
* Authors: Frank Dellaert, et al. (see THANKS for the full author list)
|
|
|
|
|
|
|
|
|
|
* See LICENSE for the license information
|
|
|
|
|
|
|
|
|
|
* -------------------------------------------------------------------------- */
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* @file DoglegOptimizer.cpp
|
|
|
|
|
* @brief
|
|
|
|
|
* @author Richard Roberts
|
2012-10-02 22:40:07 +08:00
|
|
|
* @date Feb 26, 2012
|
2012-03-23 11:38:57 +08:00
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
#include <gtsam/nonlinear/DoglegOptimizer.h>
|
|
|
|
|
#include <gtsam/nonlinear/DoglegOptimizerImpl.h>
|
2013-08-02 05:57:33 +08:00
|
|
|
#include <gtsam/linear/GaussianBayesTree.h>
|
|
|
|
|
#include <gtsam/linear/GaussianBayesNet.h>
|
|
|
|
|
#include <gtsam/linear/GaussianFactorGraph.h>
|
|
|
|
|
#include <gtsam/linear/VectorValues.h>
|
2012-03-23 11:38:57 +08:00
|
|
|
|
2012-07-19 07:35:36 +08:00
|
|
|
#include <boost/algorithm/string.hpp>
|
|
|
|
|
|
2012-03-23 11:38:57 +08:00
|
|
|
using namespace std;
|
|
|
|
|
|
|
|
|
|
namespace gtsam {
|
|
|
|
|
|
2012-07-19 07:35:36 +08:00
|
|
|
/* ************************************************************************* */
|
|
|
|
|
DoglegParams::VerbosityDL DoglegParams::verbosityDLTranslator(const std::string &verbosityDL) const {
|
2012-10-02 22:40:07 +08:00
|
|
|
std::string s = verbosityDL; boost::algorithm::to_upper(s);
|
|
|
|
|
if (s == "SILENT") return DoglegParams::SILENT;
|
|
|
|
|
if (s == "VERBOSE") return DoglegParams::VERBOSE;
|
2012-07-19 07:35:36 +08:00
|
|
|
|
2012-10-02 22:40:07 +08:00
|
|
|
/* default is silent */
|
|
|
|
|
return DoglegParams::SILENT;
|
2012-07-19 07:35:36 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/* ************************************************************************* */
|
|
|
|
|
std::string DoglegParams::verbosityDLTranslator(VerbosityDL verbosityDL) const {
|
2012-10-02 22:40:07 +08:00
|
|
|
std::string s;
|
|
|
|
|
switch (verbosityDL) {
|
|
|
|
|
case DoglegParams::SILENT: s = "SILENT"; break;
|
|
|
|
|
case DoglegParams::VERBOSE: s = "VERBOSE"; break;
|
|
|
|
|
default: s = "UNDEFINED"; break;
|
|
|
|
|
}
|
|
|
|
|
return s;
|
2012-07-19 07:35:36 +08:00
|
|
|
}
|
|
|
|
|
|
2012-04-05 07:20:42 +08:00
|
|
|
/* ************************************************************************* */
|
2012-05-15 03:10:02 +08:00
|
|
|
void DoglegOptimizer::iterate(void) {
|
2012-03-23 11:38:57 +08:00
|
|
|
|
|
|
|
|
// Linearize graph
|
2013-08-02 05:57:33 +08:00
|
|
|
GaussianFactorGraph::shared_ptr linear = graph_.linearize(state_.values);
|
2012-03-23 11:38:57 +08:00
|
|
|
|
|
|
|
|
// Pull out parameters we'll use
|
2012-05-15 21:33:32 +08:00
|
|
|
const bool dlVerbose = (params_.verbosityDL > DoglegParams::SILENT);
|
2012-03-23 11:38:57 +08:00
|
|
|
|
|
|
|
|
// Do Dogleg iteration with either Multifrontal or Sequential elimination
|
|
|
|
|
DoglegOptimizerImpl::IterationResult result;
|
|
|
|
|
|
2012-05-25 23:26:30 +08:00
|
|
|
if ( params_.isMultifrontal() ) {
|
2013-08-02 05:57:33 +08:00
|
|
|
GaussianBayesTree bt = *linear->eliminateMultifrontal(*params_.ordering, params_.getEliminationFunction());
|
2013-08-10 05:35:45 +08:00
|
|
|
VectorValues dx_u = bt.optimizeGradientSearch();
|
|
|
|
|
VectorValues dx_n = bt.optimize();
|
|
|
|
|
result = DoglegOptimizerImpl::Iterate(state_.Delta, DoglegOptimizerImpl::ONE_STEP_PER_ITERATION,
|
|
|
|
|
dx_u, dx_n, bt, graph_, state_.values, state_.error, dlVerbose);
|
2012-05-25 23:26:30 +08:00
|
|
|
}
|
|
|
|
|
else if ( params_.isSequential() ) {
|
2013-08-02 05:57:33 +08:00
|
|
|
GaussianBayesNet bn = *linear->eliminateSequential(*params_.ordering, params_.getEliminationFunction());
|
2013-08-10 05:35:45 +08:00
|
|
|
VectorValues dx_u = bn.optimizeGradientSearch();
|
|
|
|
|
VectorValues dx_n = bn.optimize();
|
|
|
|
|
result = DoglegOptimizerImpl::Iterate(state_.Delta, DoglegOptimizerImpl::ONE_STEP_PER_ITERATION,
|
|
|
|
|
dx_u, dx_n, bn, graph_, state_.values, state_.error, dlVerbose);
|
2012-05-25 23:26:30 +08:00
|
|
|
}
|
2014-06-04 11:52:35 +08:00
|
|
|
else if ( params_.isIterative() ) {
|
2013-08-10 05:35:45 +08:00
|
|
|
throw runtime_error("Dogleg is not currently compatible with the linear conjugate gradient solver");
|
2012-05-25 23:26:30 +08:00
|
|
|
}
|
|
|
|
|
else {
|
2012-03-23 11:38:57 +08:00
|
|
|
throw runtime_error("Optimization parameter is invalid: DoglegParams::elimination");
|
|
|
|
|
}
|
|
|
|
|
|
2012-04-05 10:45:47 +08:00
|
|
|
// Maybe show output
|
2012-05-15 02:11:52 +08:00
|
|
|
if(params_.verbosity >= NonlinearOptimizerParams::DELTA) result.dx_d.print("delta");
|
2012-04-05 07:20:42 +08:00
|
|
|
|
2012-04-05 10:45:47 +08:00
|
|
|
// Create new state with new values and new error
|
2013-08-02 05:57:33 +08:00
|
|
|
state_.values = state_.values.retract(result.dx_d);
|
2012-05-15 02:11:52 +08:00
|
|
|
state_.error = result.f_error;
|
2012-05-15 03:10:02 +08:00
|
|
|
state_.Delta = result.Delta;
|
2012-05-15 02:11:52 +08:00
|
|
|
++state_.iterations;
|
2012-04-05 07:20:42 +08:00
|
|
|
}
|
|
|
|
|
|
2013-08-02 05:57:33 +08:00
|
|
|
/* ************************************************************************* */
|
|
|
|
|
DoglegParams DoglegOptimizer::ensureHasOrdering(DoglegParams params, const NonlinearFactorGraph& graph) const {
|
2015-02-14 00:17:11 +08:00
|
|
|
if (!params.ordering)
|
|
|
|
|
params.ordering = Ordering::Create(params.orderingType, graph);
|
2013-08-02 05:57:33 +08:00
|
|
|
return params;
|
|
|
|
|
}
|
|
|
|
|
|
2012-03-23 11:38:57 +08:00
|
|
|
} /* namespace gtsam */
|