Jafar
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines
gicp.hpp
00001 #ifndef ICP_GICP_HPP
00002 #define ICP_GICP_HPP
00003 
00004 #include "jmath/jblas.hpp"
00005 #include "kernel/jafarMacro.hpp"
00006 #include "geom/t3dEuler.hpp"
00007 #include <lbfgs.h>
00008 #include <ANN.h>
00009 #include <gsl/gsl_vector.h>
00010 namespace jafar {
00011   namespace icp {
00021     class GICP {
00022     private:
00024       ANNpointArray m_model_points;
00026       ANNpointArray m_scene_points;
00028       ANNkd_tree *m_model_tree;
00029       ANNkd_tree *m_scene_tree;
00031       unsigned int m_model_nb_points;
00033       unsigned int m_scene_nb_points;
00034       
00035       jblas::mat R,t;
00036       int m_K;
00037       double m_epsilon;
00038       double m_max_dist;
00040       //      typedef std::vector< cv::Mat > covariances;
00041       typedef std::vector< jblas::mat_column_major > covariances;
00042       // typedef typename std:vector< cv::Mat >::iterator a_covariance;
00044       covariances m_scene_covs;
00046       covariances m_model_covs;
00048       int m_max_iter;
00050       int m_lbfgs_max_iter;
00052       lbfgs_parameter_t m_lbfgs_param;
00054       double m_lbfgs_ftol;
00056       double m_lbfgs_gtol;
00058       double* m_x;
00060       double m_fx;
00061       int nb_matches;
00062       geom::T3D *initial_t3d;
00063       geom::T3D *final_t3d;
00064       std::vector<jblas::mat_column_major> mahalanobis;
00065       //      std::vector< cv::Mat > indexes;
00066       //      std::vector< cv::Mat > distances;
00067       ANNidx *indexes;
00068       std::vector< ANNdist > distances;
00069 
00070       static double _evaluate(void* instance,
00071                               const double *x,
00072                               double *g,
00073                               const int n,
00074                               const double step);
00075       double evaluate(const double *x,
00076                       double *g,
00077                       const int n,
00078                       const double step);
00079 
00080       static int _progress(void* instance,
00081                            const double *x,
00082                    const double *g,
00083                    const double fx,
00084                    const double xnorm,
00085                    const double gnorm,
00086                    const double step,
00087                    int n,
00088                    int k,
00089                    int ls);
00090 
00091       int progress(const double *x,
00092                    const double *g,
00093                    const double fx,
00094                    const double xnorm,
00095                    const double gnorm,
00096                    const double step,
00097                    int n,
00098                    int k,
00099                    int ls);
00100 
00101 // compute trace of a^t.b
00102 inline double trace_at_b(const jblas::mat &a, const jblas::mat& b) {
00103   JFR_ASSERT(a.size1() == b.size2(), "matrices need to be multipliable")
00104   double trace = 0.;
00105   int n = a.size1();
00106   for(int i = 0; i < n; i++)
00107     for(int j = 0; j < n; j++)
00108       trace+= a(j,i) * b(i,j);
00109 
00110   return trace;
00111 }
00112 
00113 public: 
00114       GICP(size_t max_nb_points = 1024, double epsilon = 1e-3, double max_dist = 5., 
00115            int K = 20, int max_iter = 100,
00116            int inner_max_iter = 8, double ftol = 0.01, double gtol = 0.01) : 
00117         m_K(K), m_epsilon(epsilon), m_max_dist(max_dist), m_max_iter(max_iter), 
00118         m_lbfgs_max_iter(inner_max_iter), m_lbfgs_ftol(ftol), m_lbfgs_gtol(gtol),
00119         m_model_nb_points(0), m_scene_nb_points(0), 
00120         mahalanobis(0),
00121         indexes(0), 
00122         distances(0)
00123       {
00124         m_model_points = annAllocPts(max_nb_points, 3);
00125         m_scene_points = annAllocPts(max_nb_points, 3);
00126       }
00127 
00128       GICP(const jblas::mat& model, jblas::mat& scene, 
00129            double epsilon = 1e-3, double max_dist = 5., 
00130            int K = 20, int max_iter = 100, 
00131            int inner_max_iter = 8, double ftol = 0.01, double gtol = 0.01) : 
00132         m_K(K), m_epsilon(epsilon), m_max_dist(max_dist), m_max_iter(max_iter), 
00133         m_lbfgs_max_iter(inner_max_iter), m_lbfgs_ftol(ftol), m_lbfgs_gtol(gtol),
00134         // indexes(m_model.rows, cv::Mat(1, 1, CV_32S)), 
00135         // distances(m_model.rows, cv::Mat(1, 1, CV_32F)),
00136         m_model_nb_points(model.size1()),
00137         m_scene_nb_points(scene.size1()),
00138         mahalanobis(0)
00139       {
00140         using namespace std;
00141         m_model_points = annAllocPts(m_model_nb_points, 3);
00142         m_scene_points = annAllocPts(m_scene_nb_points, 3);
00143         for (unsigned int mrow = 0; mrow < m_model_nb_points; mrow++) {
00144           m_model_points[mrow][0] = model(mrow,0);
00145           m_model_points[mrow][1] = model(mrow,1);
00146           m_model_points[mrow][2] = model(mrow,2);
00147         }
00148         cout << "loaded "<<m_model_nb_points<<" points for the model"<<endl;
00149         for (unsigned int srow = 0; srow < m_scene_nb_points; srow++) {
00150           m_scene_points[srow][0] = scene(srow,0);
00151           m_scene_points[srow][1] = scene(srow,1);
00152           m_scene_points[srow][2] = scene(srow,2);
00153         }
00154         cout << "loaded "<<m_scene_nb_points<<" points for the scene"<<endl;
00155       }
00156 
00157       void addModelEntry(const jblas::vec3& entry)
00158       {
00159         m_model_points[m_model_nb_points][0] = entry[0];
00160         m_model_points[m_model_nb_points][1] = entry[1];
00161         m_model_points[m_model_nb_points][2] = entry[2];
00162         ++m_model_nb_points;
00163       }
00164 
00165       void addSceneEntry(const jblas::vec3& entry)
00166       {
00167         m_scene_points[m_scene_nb_points][0] = entry[0];
00168         m_scene_points[m_scene_nb_points][1] = entry[1];
00169         m_scene_points[m_scene_nb_points][2] = entry[2];
00170         ++m_scene_nb_points;
00171       }
00172 
00173       inline void transform(const geom::T3D* t, jblas::vec3& pt) {
00174         jblas::mat44 M = t->getM();
00175         assert(M(3,3) == 1);
00176         double x, y, z;
00177         x = (M(0,0) * pt[0]) + (M(0,1) * pt[1]) + (M(0,2) * pt[2]) + M(0,3);
00178         y = (M(1,0) * pt[0]) + (M(1,1) * pt[1]) + (M(1,2) * pt[2]) + M(1,3);
00179         z = (M(2,0) * pt[0]) + (M(2,1) * pt[1]) + (M(2,2) * pt[2]) + M(2,3);
00180         pt[0] = x;
00181         pt[1] = y;
00182         pt[2] = z;
00183       }
00184 
00186       void computeCovarianceMatrices(const ANNpointArray& points, 
00187                                      size_t nb_points,
00188                                      ANNkd_tree* points_tree,
00189                                      covariances& points_covariances);
00190 
00192       int align(const ANNpointArray& model_points, unsigned int nb_model_points, 
00193                 const covariances& model_covariances,
00194                 const ANNpointArray& scene_points, ANNkd_tree* scene_tree, 
00195                 const covariances& scene_covariances,
00196                 const geom::T3D *guess, geom::T3D *t);
00197       int align_gsl(const ANNpointArray& model, unsigned int nb_model_points, 
00198                     const covariances& model_covariances,
00199                     const ANNpointArray& scene, ANNkd_tree* scene_tree,
00200                     const covariances& scene_covariances,
00201                     const geom::T3D *guess, geom::T3D *t);
00203       void run(geom::T3DEuler *guess = NULL) 
00204       {
00205         using namespace std;
00206         //build kd tree for the model points
00207         m_model_tree = new ANNkd_tree(m_model_points, m_model_nb_points, 3, 10);
00208         cout << "m_model_index created" << endl;
00209         computeCovarianceMatrices(m_model_points, m_model_nb_points, m_model_tree, m_model_covs);
00210         //build kd tree for the scene points
00211         m_scene_tree = new ANNkd_tree(m_scene_points, m_scene_nb_points, 3, 10);
00212         cout << "m_scene_index created" << endl;
00213         computeCovarianceMatrices(m_scene_points, m_scene_nb_points, m_scene_tree, m_scene_covs);
00214         
00215         final_t3d = geom::T3D::create(geom::T3D::EULER);
00216         initial_t3d = geom::T3D::create(geom::T3D::EULER);
00217         initial_t3d->set(jblas::identity_mat(3,3), jblas::zero_vec(3));
00218         final_t3d->set(jblas::identity_mat(3,3), jblas::zero_vec(3));
00219         if(guess != NULL) 
00220         {
00221           initial_t3d = guess;
00222         } 
00223 
00224         //  align(m_model_points, m_model_nb_points, m_scene_points, m_scene_tree, initial_t3d, t1);
00225         //align(m_model_points, m_model_nb_points, m_model_covs, m_scene_points, m_scene_tree, m_scene_covs, initial_t3d, final_t3d);
00226         align_gsl(m_model_points, m_model_nb_points, m_model_covs, m_scene_points, m_scene_tree, m_scene_covs, initial_t3d, final_t3d);
00227         //  cout << "guess " << *guess << endl;
00228         cout << "initial t3d" << initial_t3d->getM() << endl;
00229         cout << "final t3d" << final_t3d->getM() << endl;
00230       }
00231       double f(const gsl_vector *x, void *params);
00232       void df(const gsl_vector *x, void *params, gsl_vector *g);
00233       void fdf(const gsl_vector *x, void *params, double *f, gsl_vector *g);
00234       geom::T3D* get_final_t3d() 
00235       {
00236         return final_t3d;
00237       }
00238     };
00239   }
00240 }
00241 
00242 #endif
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines

Generated on Wed Oct 15 2014 00:37:21 for Jafar by doxygen 1.7.6.1
LAAS-CNRS