5 #ifndef __pinocchio_symmetric3_hpp__ 6 #define __pinocchio_symmetric3_hpp__ 8 #include "pinocchio/macros.hpp" 9 #include "pinocchio/math/matrix.hpp" 14 template<
typename _Scalar,
int _Options>
18 typedef _Scalar Scalar;
19 enum { Options = _Options };
20 typedef Eigen::Matrix<Scalar,3,1,Options> Vector3;
21 typedef Eigen::Matrix<Scalar,6,1,Options> Vector6;
22 typedef Eigen::Matrix<Scalar,3,3,Options> Matrix3;
23 typedef Eigen::Matrix<Scalar,2,2,Options> Matrix2;
24 typedef Eigen::Matrix<Scalar,3,2,Options> Matrix32;
26 EIGEN_MAKE_ALIGNED_OPERATOR_NEW
29 Symmetric3Tpl(): m_data() {}
31 template<
typename Sc,
int N,
int Opt>
32 explicit Symmetric3Tpl(
const Eigen::Matrix<Sc,N,N,Opt> & I)
34 EIGEN_STATIC_ASSERT(N==3,THIS_METHOD_IS_ONLY_FOR_MATRICES_OF_A_SPECIFIC_SIZE)
35 assert( (I-I.transpose()).isMuchSmallerThan(I) );
37 m_data(1) = I(1,0); m_data(2) = I(1,1);
38 m_data(3) = I(2,0); m_data(4) = I(2,1); m_data(5) = I(2,2);
41 explicit Symmetric3Tpl(
const Vector6 & I) : m_data(I) {}
43 Symmetric3Tpl(
const Scalar & a0,
const Scalar & a1,
const Scalar & a2,
44 const Scalar & a3,
const Scalar & a4,
const Scalar & a5)
45 { m_data << a0,a1,a2,a3,a4,a5; }
47 static Symmetric3Tpl Zero() {
return Symmetric3Tpl(Vector6::Zero()); }
48 void setZero() { m_data.setZero(); }
50 static Symmetric3Tpl Random() {
return RandomPositive(); }
54 a = Scalar(std::rand())/RAND_MAX*2.0-1.0,
55 b = Scalar(std::rand())/RAND_MAX*2.0-1.0,
56 c = Scalar(std::rand())/RAND_MAX*2.0-1.0,
57 d = Scalar(std::rand())/RAND_MAX*2.0-1.0,
58 e = Scalar(std::rand())/RAND_MAX*2.0-1.0,
59 f = Scalar(std::rand())/RAND_MAX*2.0-1.0;
61 m_data << a, b, c, d, e, f;
64 static Symmetric3Tpl Identity() {
return Symmetric3Tpl(1, 0, 1, 0, 0, 1); }
65 void setIdentity() { m_data << 1, 0, 1, 0, 0, 1; }
68 bool operator==(
const Symmetric3Tpl & other)
const 69 {
return m_data == other.m_data; }
71 bool operator!=(
const Symmetric3Tpl & other)
const 72 {
return !(*
this == other); }
74 bool isApprox(
const Symmetric3Tpl & other,
75 const Scalar & prec = Eigen::NumTraits<Scalar>::dummy_precision())
const 76 {
return m_data.isApprox(other.m_data,prec); }
78 bool isZero(
const Scalar & prec = Eigen::NumTraits<Scalar>::dummy_precision())
const 79 {
return m_data.isZero(prec); }
81 void fill(
const Scalar value) { m_data.fill(value); }
89 const Scalar & x = v[0], & y = v[1], & z = v[2];
92 x*z , y*z , -x*x-y*y );
98 const Scalar & x = v.v[0], & y = v.v[1], & z = v.v[2];
100 m_data[1]-x*y,m_data[2]+x*x+z*z,
101 m_data[3]-x*z,m_data[4]-y*z,m_data[5]+x*x+y*y);
106 const Scalar & x = v.v[0], & y = v.v[1], & z = v.v[2];
108 m_data[1]-=x*y; m_data[2]+=x*x+z*z;
109 m_data[3]-=x*z; m_data[4]-=y*z; m_data[5]+=x*x+y*y;
114 friend Matrix3 operator- (
const Symmetric3Tpl & S,
const Eigen::MatrixBase <D> & M)
116 EIGEN_STATIC_ASSERT_MATRIX_SPECIFIC_SIZE(D,3,3);
117 Matrix3 result (S.matrix());
133 const Scalar & x = v[0], & y = v[1], & z = v[2];
136 m* x*z,m* y*z,-m*(x*x+y*y));
145 const Scalar & x = v.v[0], & y = v.v[1], & z = v.v[2];
147 m_data[1]-v.m* x*y, m_data[2]+v.m*(x*x+z*z),
148 m_data[3]-v.m* x*z, m_data[4]-v.m* y*z,
149 m_data[5]+v.m*(x*x+y*y));
154 const Scalar & x = v.v[0], & y = v.v[1], & z = v.v[2];
155 m_data[0]+=v.m*(y*y+z*z);
156 m_data[1]-=v.m* x*y; m_data[2]+=v.m*(x*x+z*z);
157 m_data[3]-=v.m* x*z; m_data[4]-=v.m* y*z; m_data[5]+=v.m*(x*x+y*y);
161 const Vector6 & data ()
const {
return m_data;}
162 Vector6 & data () {
return m_data;}
176 a = Scalar(std::rand())/RAND_MAX*2.0-1.0,
177 b = Scalar(std::rand())/RAND_MAX*2.0-1.0,
178 c = Scalar(std::rand())/RAND_MAX*2.0-1.0,
179 d = Scalar(std::rand())/RAND_MAX*2.0-1.0,
180 e = Scalar(std::rand())/RAND_MAX*2.0-1.0,
181 f = Scalar(std::rand())/RAND_MAX*2.0-1.0;
183 a*b+b*c+d*e, b*b+c*c+e*e,
184 a*d+b*e+d*f, b*d+c*e+e*f, d*d+e*e+f*f );
187 Matrix3 matrix()
const 190 res(0,0) = m_data(0); res(0,1) = m_data(1); res(0,2) = m_data(3);
191 res(1,0) = m_data(1); res(1,1) = m_data(2); res(1,2) = m_data(4);
192 res(2,0) = m_data(3); res(2,1) = m_data(4); res(2,2) = m_data(5);
195 operator Matrix3 ()
const {
return matrix(); }
197 Scalar vtiv (
const Vector3 & v)
const 199 const Scalar & x = v[0];
200 const Scalar & y = v[1];
201 const Scalar & z = v[2];
203 const Scalar xx = x*x;
204 const Scalar xy = x*y;
205 const Scalar xz = x*z;
206 const Scalar yy = y*y;
207 const Scalar yz = y*z;
208 const Scalar zz = z*z;
210 return m_data(0)*xx + m_data(2)*yy + m_data(5)*zz + 2.*(m_data(1)*xy + m_data(3)*xz + m_data(4)*yz);
223 template<
typename Vector3,
typename Matrix3>
224 static void vxs(
const Eigen::MatrixBase<Vector3> & v,
226 const Eigen::MatrixBase<Matrix3> & M)
228 EIGEN_STATIC_ASSERT_VECTOR_SPECIFIC_SIZE(Vector3,3);
229 EIGEN_STATIC_ASSERT_MATRIX_SPECIFIC_SIZE(Matrix3,3,3);
231 const Scalar & a = S3.data()[0];
232 const Scalar & b = S3.data()[1];
233 const Scalar & c = S3.data()[2];
234 const Scalar & d = S3.data()[3];
235 const Scalar & e = S3.data()[4];
236 const Scalar & f = S3.data()[5];
239 const typename Vector3::RealScalar & v0 = v[0];
240 const typename Vector3::RealScalar & v1 = v[1];
241 const typename Vector3::RealScalar & v2 = v[2];
243 Matrix3 & M_ = PINOCCHIO_EIGEN_CONST_CAST(Matrix3,M);
244 M_(0,0) = d * v1 - b * v2;
245 M_(1,0) = a * v2 - d * v0;
246 M_(2,0) = b * v0 - a * v1;
248 M_(0,1) = e * v1 - c * v2;
249 M_(1,1) = b * v2 - e * v0;
250 M_(2,1) = c * v0 - b * v1;
252 M_(0,2) = f * v1 - e * v2;
253 M_(1,2) = d * v2 - f * v0;
254 M_(2,2) = e * v0 - d * v1;
267 template<
typename Vector3>
268 Matrix3
vxs(
const Eigen::MatrixBase<Vector3> & v)
const 284 template<
typename Vector3,
typename Matrix3>
285 static void svx(
const Eigen::MatrixBase<Vector3> & v,
287 const Eigen::MatrixBase<Matrix3> & M)
289 EIGEN_STATIC_ASSERT_VECTOR_SPECIFIC_SIZE(Vector3,3);
290 EIGEN_STATIC_ASSERT_MATRIX_SPECIFIC_SIZE(Matrix3,3,3);
292 const Scalar & a = S3.data()[0];
293 const Scalar & b = S3.data()[1];
294 const Scalar & c = S3.data()[2];
295 const Scalar & d = S3.data()[3];
296 const Scalar & e = S3.data()[4];
297 const Scalar & f = S3.data()[5];
299 const typename Vector3::RealScalar & v0 = v[0];
300 const typename Vector3::RealScalar & v1 = v[1];
301 const typename Vector3::RealScalar & v2 = v[2];
303 Matrix3 & M_ = PINOCCHIO_EIGEN_CONST_CAST(Matrix3,M);
304 M_(0,0) = b * v2 - d * v1;
305 M_(1,0) = c * v2 - e * v1;
306 M_(2,0) = e * v2 - f * v1;
308 M_(0,1) = d * v0 - a * v2;
309 M_(1,1) = e * v0 - b * v2;
310 M_(2,1) = f * v0 - d * v2;
312 M_(0,2) = a * v1 - b * v0;
313 M_(1,2) = b * v1 - c * v0;
314 M_(2,2) = d * v1 - e * v0;
325 template<
typename Vector3>
326 Matrix3
svx(
const Eigen::MatrixBase<Vector3> & v)
const 340 m_data += s2.m_data;
return *
this;
343 template<
typename V3in,
typename V3out>
345 const Eigen::MatrixBase<V3in> & vin,
346 const Eigen::MatrixBase<V3out> & vout)
348 EIGEN_STATIC_ASSERT_SAME_VECTOR_SIZE(V3in,Vector3);
349 EIGEN_STATIC_ASSERT_SAME_VECTOR_SIZE(V3out,Vector3);
351 V3out & vout_ = PINOCCHIO_EIGEN_CONST_CAST(V3out,vout);
353 vout_[0] = S3.m_data(0) * vin[0] + S3.m_data(1) * vin[1] + S3.m_data(3) * vin[2];
354 vout_[1] = S3.m_data(1) * vin[0] + S3.m_data(2) * vin[1] + S3.m_data(4) * vin[2];
355 vout_[2] = S3.m_data(3) * vin[0] + S3.m_data(4) * vin[1] + S3.m_data(5) * vin[2];
358 template<
typename V3>
359 Vector3
operator*(
const Eigen::MatrixBase<V3> & v)
const 362 rhsMult(*
this,v,res);
378 const Scalar& operator()(
const int &i,
const int &j)
const 380 return ((i!=2)&&(j!=2)) ? m_data[i+j] : m_data[i+j+1];
385 assert( (S-S.transpose()).isMuchSmallerThan(S) );
387 m_data(1)-S(1,0), m_data(2)-S(1,1),
388 m_data(3)-S(2,0), m_data(4)-S(2,1), m_data(5)-S(2,2) );
393 assert( (S-S.transpose()).isMuchSmallerThan(S) );
395 m_data(1)+S(1,0), m_data(2)+S(1,1),
396 m_data(3)+S(2,0), m_data(4)+S(2,1), m_data(5)+S(2,2) );
408 m_data(0) - m_data(5), m_data(1),
409 m_data(1), m_data(2) - m_data(5),
410 2*m_data(3), m_data(4) + m_data(4);
418 EIGEN_STATIC_ASSERT_MATRIX_SPECIFIC_SIZE(D,3,3);
419 assert(
isUnitary(R.transpose()*R) &&
"R is not a Unitary matrix");
427 const Matrix2 Y( R.template block<2,3>(1,0) * L );
430 Sres.m_data(1) = Y(0,0)*R(0,0) + Y(0,1)*R(0,1);
431 Sres.m_data(2) = Y(0,0)*R(1,0) + Y(0,1)*R(1,1);
432 Sres.m_data(3) = Y(1,0)*R(0,0) + Y(1,1)*R(0,1);
433 Sres.m_data(4) = Y(1,0)*R(1,0) + Y(1,1)*R(1,1);
434 Sres.m_data(5) = Y(1,0)*R(2,0) + Y(1,1)*R(2,1);
437 const Vector3 r(-R(0,0)*m_data(4) + R(0,1)*m_data(3),
438 -R(1,0)*m_data(4) + R(1,1)*m_data(3),
439 -R(2,0)*m_data(4) + R(2,1)*m_data(3));
442 Sres.m_data(0) = L(0,0) + L(1,1) - Sres.m_data(2) - Sres.m_data(5);
445 Sres.m_data(0) += m_data(5);
446 Sres.m_data(1) += r(2); Sres.m_data(2)+= m_data(5);
447 Sres.m_data(3) +=-r(1); Sres.m_data(4)+= r(0); Sres.m_data(5) += m_data(5);
453 template<
typename NewScalar>
466 #endif // ifndef __pinocchio_symmetric3_hpp__
Matrix32 decomposeltI() const
Computes L for a symmetric matrix A.
bool isUnitary(const Eigen::MatrixBase< MatrixLike > &mat, const typename MatrixLike::RealScalar &prec=Eigen::NumTraits< typename MatrixLike::Scalar >::dummy_precision())
Check whether the input matrix is Unitary within the given precision.
Matrix3 vxs(const Eigen::MatrixBase< Vector3 > &v) const
Performs the operation . This operation is equivalent to applying the cross product of v on each colu...
static void vxs(const Eigen::MatrixBase< Vector3 > &v, const Symmetric3Tpl &S3, const Eigen::MatrixBase< Matrix3 > &M)
Performs the operation . This operation is equivalent to applying the cross product of v on each colu...
Main pinocchio namespace.
static void svx(const Eigen::MatrixBase< Vector3 > &v, const Symmetric3Tpl &S3, const Eigen::MatrixBase< Matrix3 > &M)
Performs the operation .
Matrix3 svx(const Eigen::MatrixBase< Vector3 > &v) const
Performs the operation .
Symmetric3Tpl< NewScalar, Options > cast() const
MultiplicationOp< InertiaTpl< Scalar, Options >, ConstraintDerived >::ReturnType operator*(const InertiaTpl< Scalar, Options > &Y, const ConstraintBase< ConstraintDerived > &constraint)
.