posegraph.hpp
Go to the documentation of this file.
00001 // HOG-Man - Hierarchical Optimization for Pose Graphs on Manifolds
00002 // Copyright (C) 2010 G. Grisetti, R. Kümmerle, C. Stachniss
00003 // 
00004 // HOG-Man is free software: you can redistribute it and/or modify
00005 // it under the terms of the GNU Lesser General Public License as published
00006 // by the Free Software Foundation, either version 3 of the License, or
00007 // (at your option) any later version.
00008 // 
00009 // HOG-Man is distributed in the hope that it will be useful,
00010 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00011 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00012 // GNU Lesser General Public License for more details.
00013 // 
00014 // You should have received a copy of the GNU Lesser General Public License
00015 // along with this program.  If not, see <http://www.gnu.org/licenses/>.
00016 
00017 #include <assert.h>
00018 #include <queue>
00019 #include <iostream>
00020 #include <iomanip>
00021 //#include "posegraph2d.hh"
00022 
00023 #define LINESIZE (4096*4)
00024 
00025 namespace AISNavigation{
00026   using namespace std;
00027 
00028   template <typename T, typename I>
00029   PoseGraph<T,I>::Vertex::Vertex(int i) : Graph::Vertex(i){
00030     _tempIndex=-1;
00031     _isBackup=false;
00032     _fixed=false;
00033   }
00034 
00035   template <typename T, typename I>
00036   PoseGraph<T,I>::Vertex::~Vertex(){
00037   }
00038 
00039   template <typename T, typename I>
00040   PoseGraph<T,I>::Edge::Edge(PoseGraph<T,I>::Vertex* from, PoseGraph<T,I>::Vertex* to, const PoseGraph<T,I>::TransformationType& m, const PoseGraph<T,I>::InformationType& i) : Graph::Edge(from, to){
00041     setAttributes(m,i);
00042   }
00043 
00044   template <typename T, typename I>
00045   bool PoseGraph<T,I>::Edge::direction(Vertex* from_, Vertex* to_) const {
00046     if ((to_==_to)&&(from_==_from))
00047       return true;
00048     if ((to_==_from)&&(from_==_to))
00049       return false;
00050     assert(0);
00051     return false;
00052   }
00053 
00054   template <typename T, typename I>
00055   const typename PoseGraph<T,I>::TransformationType& PoseGraph<T,I>::Edge::mean(bool direct) const {
00056     return direct ? _mean : _rmean;
00057   }
00058 
00059   template <typename T, typename I>
00060   const typename PoseGraph<T,I>::InformationType& PoseGraph<T,I>::Edge::information(bool direct) const {
00061     return direct ? _information :_rinformation;
00062   }
00063 
00064   template <typename T, typename I>
00065   const typename PoseGraph<T,I>::InformationType& PoseGraph<T,I>::Edge::covariance(bool direct) const {
00066     return direct ? _covariance : _rcovariance;
00067   }
00068 
00069   template <typename T, typename I>
00070   const double&    PoseGraph<T,I>::Edge::informationDet(bool direct) const{
00071     return direct ? _infoDet : _rinfoDet;
00072   }
00073 
00074   template <typename T, typename I>
00075   const double&    PoseGraph<T,I>::Edge::covarianceDet(bool direct) const {
00076     return direct ? _covDet : _rcovDet;
00077   }
00078 
00079   template <typename T, typename I>
00080   bool PoseGraph<T,I>::Edge::revert(){
00081     typename PoseGraph<T,I>::TransformationType t_ap(_mean);
00082     _mean=_rmean;
00083     _rmean=t_ap;
00084     typename PoseGraph<T,I>::InformationType i_ap(_information);
00085     _information=_rinformation;
00086     _rinformation=i_ap;
00087     typename PoseGraph<T,I>::InformationType c_ap(_covariance);
00088     _covariance=_rcovariance;
00089     _rcovariance=c_ap;
00090     double id_ap=_infoDet;
00091     _infoDet=_rinfoDet;
00092     _rinfoDet=id_ap;
00093     double ic_ap=_covDet;
00094     _covDet=_rcovDet;
00095     _rcovDet=ic_ap;
00096     return Graph::Edge::revert();
00097   }
00098 
00099   template <typename T, typename I>
00100   void PoseGraph<T,I>::Edge::setAttributes(const PoseGraph<T,I>::TransformationType& mean_, const PoseGraph<T,I>::InformationType& information_){
00101     _mean=mean_;
00102     _information=information_;
00103 
00104     _covariance=information_.inverse();
00105     _infoDet=information_.det();
00106     _covDet=1./_infoDet;
00107     _rmean=mean_.inverse();
00108     //HACK, should use jacobians to project the information matrices and
00109     //the covariances
00110     _rinformation=_information;
00111     _rcovariance=_covariance;
00112     _rinfoDet=_infoDet;
00113     _rcovDet=_covDet;
00114   }
00115 
00116   template <typename T, typename I>
00117   double PoseGraph<T,I>::Edge::chi2() const{
00118     typename PoseGraph<T,I>::Vertex* v1 = reinterpret_cast<typename PoseGraph<T,I>::Vertex*>(_from);
00119     typename PoseGraph<T,I>::Vertex* v2 = reinterpret_cast<typename PoseGraph<T,I>::Vertex*>(_to);
00120     typename PoseGraph<T,I>::TransformationType delta=_rmean * (v1->transformation.inverse()*v2->transformation);
00121     typename PoseGraph<T,I>::TransformationVectorType dp=delta.toVector();
00122     typename PoseGraph<T,I>::TransformationVectorType partial=_information*dp;
00123     return dp*partial;
00124   }
00125 
00126   template <typename T, typename I>
00127   double PoseGraph<T,I>::PathLengthCostFunction::operator()(Graph::Edge* edge, Graph::Vertex* from, Graph::Vertex* to){
00128     const typename PoseGraph<T,I>::Edge* e=dynamic_cast<const typename PoseGraph<T,I>::Edge*>(edge);
00129     typename T::TranslationType t=e->mean().translation();
00130     return sqrt(t*t);
00131   }
00132 
00133   template <typename T, typename I>
00134   double PoseGraph<T,I>::CovarianceDetCostFunction::operator()(Graph::Edge* edge, Graph::Vertex* from, Graph::Vertex* to){
00135     const typename PoseGraph<T,I>::Edge* e=dynamic_cast<const typename PoseGraph<T,I>::Edge*>(edge);
00136     return e->covarianceDet();
00137   }
00138 
00139 
00140   template <typename T, typename I>
00141   typename PoseGraph<T,I>::Vertex* PoseGraph<T,I>::addVertex(const int& k){
00142     Vertex* v=new typename PoseGraph<T,I>::Vertex(k);
00143     Vertex* vresult=dynamic_cast<typename PoseGraph<T,I>::Vertex*>(Graph::addVertex(v));
00144     if (!vresult){
00145       delete v;
00146     }
00147     return vresult;
00148   }
00149 
00150   template <typename T, typename I>
00151   typename PoseGraph<T,I>::Vertex* PoseGraph<T,I>::addVertex(int id, const PoseGraph<T,I>::TransformationType& pose, const PoseGraph<T,I>::InformationType& information){
00152     typename PoseGraph<T,I>::Vertex* v=new typename PoseGraph<T,I>::Vertex(id);
00153     typename PoseGraph<T,I>::Vertex* vresult=dynamic_cast< typename PoseGraph<T,I>::Vertex*>(Graph::addVertex(v));
00154     if (!vresult){
00155       delete v;
00156       return vresult;
00157     }
00158     vresult->transformation=pose;
00159     vresult->covariance=information.inverse();
00160     return vresult;
00161   }
00162 
00163   template <typename T, typename I>
00164   typename PoseGraph<T,I>::Edge*   PoseGraph<T,I>::addEdge(Vertex* from, Vertex* to, const PoseGraph<T,I>::TransformationType& mean, const PoseGraph<T,I>::InformationType& information) {
00165     typename PoseGraph<T,I>::Edge* e=new typename PoseGraph<T,I>::Edge(from, to, mean, information);
00166     typename PoseGraph<T,I>::Edge* eresult=dynamic_cast<typename PoseGraph<T,I>::Edge*>(Graph::addEdge(e));
00167     if (! eresult)
00168       delete e;
00169     return eresult;
00170   }
00171 
00172 
00173   template <typename PG>
00174   struct CovariancePropagator: public Dijkstra::TreeAction{
00175     virtual double perform(Graph::Vertex* v_, Graph::Vertex* vParent_, Graph::Edge* e_){
00176       typename PG::Vertex* v =dynamic_cast<typename PG::Vertex*>(v_);
00177       typename PG::Vertex* vParent =dynamic_cast<typename PG::Vertex*>(vParent_);
00178       typename PG::Edge* e =dynamic_cast<typename PG::Edge*>(e_);
00179       assert(v);
00180       typename PG::InformationType& cov(v->covariance);
00181       if (! vParent){
00182         cov=PG::InformationType::eye(0.);
00183         return 0;
00184       }
00185       assert(vParent);
00186       assert(e);
00187       bool direction=e->direction(vParent, v);
00188       MotionJacobian<PG> jacobian;
00189       typename PG::InformationType Jx=jacobian.state(vParent->transformation, e->mean(direction));
00190       typename PG::InformationType Ju = jacobian.measurement(vParent->transformation, e->mean(direction));
00191       v->covariance=Jx*vParent->covariance*Jx.transpose() + Ju*e->covariance()*Ju.transpose();
00192       return v->covariance.det();
00193     }
00194   };
00195 
00196   template <typename PG>
00197   struct PosePropagator: public Dijkstra::TreeAction{
00198     virtual double perform(Graph::Vertex* v_, Graph::Vertex* vParent_, Graph::Edge* e_){
00199       typename PG::Vertex* v =dynamic_cast<typename PG::Vertex*>(v_);
00200       typename PG::Vertex* vParent =dynamic_cast<typename PG::Vertex*>(vParent_);
00201       typename PG::Edge* e =dynamic_cast<typename PG::Edge*>(e_);
00202       assert(v);
00203       if (v->fixed())
00204         return 1;
00205       if (! vParent){
00206         return 0;
00207       }
00208       assert(vParent);
00209       assert(e);
00210       bool direction=e->direction(vParent, v);
00211       v->transformation=vParent->transformation*e->mean(direction);
00212       return 1;
00213     }
00214   };
00215 
00216 
00217   template <typename T, typename I>
00218   void PoseGraph<T,I>::propagateAlongDijkstraTree(typename PoseGraph<T,I>::Vertex* v, Dijkstra::AdjacencyMap& amap, bool covariance, bool transformation){
00219     Dijkstra::computeTree(v,amap);
00220     if (covariance){
00221       CovariancePropagator<PoseGraph<T,I> > cp;
00222       Dijkstra::visitAdjacencyMap(v,amap,&cp);
00223     }
00224     if (transformation){
00225       PosePropagator< PoseGraph<T,I> > tp;
00226       Dijkstra::visitAdjacencyMap(v,amap,&tp);
00227     }
00228   }
00229 
00230   template <typename T, typename I>
00231   void PoseGraph<T,I>::refineEdge(typename PoseGraph<T,I>::Edge* e, const typename PoseGraph<T,I>::TransformationType& mean, const typename PoseGraph<T,I>::InformationType& information){
00232     e->setAttributes(mean, information);
00233   }
00234 
00235 } // end namespace


hogman_minimal
Author(s): Maintained by Juergen Sturm
autogenerated on Mon Oct 6 2014 00:06:59