66 template <
typename VectorT >
69 center_of_gravity(
const std::vector< VectorT >& _points ) {
72 for (uint i = 0 ; i < _points.size() ; ++i ) {
73 cog = cog + _points[i];
76 cog = cog / (
typename VectorT::value_type )_points.size();
82 template <
typename VectorT ,
typename QuaternionT >
84 icp(
const std::vector< VectorT >& _points1 ,
const std::vector< VectorT >& _points2 ,
VectorT& _cog1 ,
VectorT& _cog2 ,
double& _scale1 ,
double& _scale2 , QuaternionT& _rotation )
87 _cog1 = center_of_gravity(_points1);
88 _cog2 = center_of_gravity(_points2);
94 for ( uint i = 0 ; i < _points1.size() ; ++i ) {
95 diff = _points1[i] - _cog1;
96 _scale1 = std::max( _scale1 , sqrt( diff.norm() ) );
97 diff = _points2[i] - _cog2;
98 _scale2 = std::max( _scale2 , sqrt( diff.norm() ) );
113 for ( uint i = 0 ; i < _points1.size() ; ++i ) {
114 Sxx += ( _points1[i][0] - _cog1[0] ) * ( _points2[i][0] - _cog2[0] );
115 Sxy += ( _points1[i][0] - _cog1[0] ) * ( _points2[i][1] - _cog2[1] );
116 Sxz += ( _points1[i][0] - _cog1[0] ) * ( _points2[i][2] - _cog2[2] );
118 Syx += ( _points1[i][1] - _cog1[1] ) * ( _points2[i][0] - _cog2[0] );
119 Syy += ( _points1[i][1] - _cog1[1] ) * ( _points2[i][1] - _cog2[1] );
120 Syz += ( _points1[i][1] - _cog1[1] ) * ( _points2[i][2] - _cog2[2] );
122 Szx += ( _points1[i][2] - _cog1[2] ) * ( _points2[i][0] - _cog2[0] );
123 Szy += ( _points1[i][2] - _cog1[2] ) * ( _points2[i][1] - _cog2[1] );
124 Szz += ( _points1[i][2] - _cog1[2] ) * ( _points2[i][2] - _cog2[2] );
127 const double scale = _scale1 * _scale2;
129 Sxx = Sxx * 1.0 / scale;
130 Sxy = Sxy * 1.0 / scale;
131 Sxz = Sxz * 1.0 / scale;
132 Syx = Syx * 1.0 / scale;
133 Syy = Syy * 1.0 / scale;
134 Syz = Syz * 1.0 / scale;
135 Szx = Szx * 1.0 / scale;
136 Szy = Szy * 1.0 / scale;
137 Szz = Szz * 1.0 / scale;
139 gmm::dense_matrix<double> N; gmm::resize(N,4,4); gmm::clear(N);
140 N(0,0) = Sxx + Syy + Szz;
146 N(1,1) = Sxx - Syy - Szz;
152 N(2,2) = -Sxx + Syy - Szz;
158 N(3,3) = -Sxx - Syy + Szz;
160 std::vector< double > eigval; eigval.resize(4);
161 gmm::dense_matrix< double > eigvect; gmm::resize(eigvect, 4,4); gmm::clear(eigvect);
162 gmm::symmetric_qr_algorithm(N, eigval, eigvect);
165 double max = -FLT_MAX;
166 for (
int i = 0; i < 4; i++)
173 _rotation[0] = eigvect(0,gr);
174 _rotation[1] = eigvect(1,gr);
175 _rotation[2] = eigvect(2,gr);
176 _rotation[3] = eigvect(3,gr);