This forum has been archived. All content is frozen. Please use KDE Discuss instead.

Strange Quaternion behavior

Tags: None
(comma "," separated)
krockot
Registered Member
Posts
1
Karma
0

Strange Quaternion behavior

Fri Jul 16, 2010 3:57 am
I posted a bug on the bitbucket site, but in retrospect I probably should have brought my issue here first. Without further ado...

I'm encountering unexpected behavior with Quaternion assignment when using MSVC9 (SP1). I have not had an opportunity to test other platforms yet*, and it is unclear to me whether this is a compiler bug, an Eigen bug, or perhaps a combination of both. Any feedback would be greatly appreciated.

*EDIT: Since posting this, I have tested the code using GCC 4.3 with vectorization enabled and it does not exhibit the same problem.

The code below demonstrates the following important points:

  • There is some problem when assigning to an initialized Quaternion object (qc below) using my cast operator in FourFloats.
  • Quaternion assignment from the cast operator does not elicit the same problem when taking place during Quaternion initialization (as demonstrated by the initialization of qa).
  • MakeQuaternion(), the plain-old-method equivalent to the Quaternion cast operator, does not elicit the problem when its result is assigned to qd after initialization.
  • The Vector4 vc does not elicit the same problem as qc, despite being another aligned Eigen type that is assigned in a manner which should be functionally equivalent to how qc is assigned.

Here's the code:

Code: Select all
#include <Eigen/Core>
#include <Eigen/Geometry>
#include <iostream>

typedef Eigen::Matrix<float,1,4> Vector4;
typedef Eigen::Quaternion<float> Quaternion;

class FourFloats
{
public:
   FourFloats( float w, float x, float y, float z ) : w(w), x(x), y(y), z(z) {}
   operator Quaternion() const { return Quaternion( w, x, y, z ); }
   operator Vector4() const { return Vector4( x, y, z, w ); }
   Quaternion MakeQuaternion() const {   return Quaternion( w, x, y, z ); }
   Vector4 MakeVector4() const { return Vector4( x, y, z, w ); }
   float w, x, y, z;
};

int main( int argc, char *argv[] )
{
   FourFloats f( 1, 2, 3, 4 );

   Vector4 va = f, vb = f.MakeVector4(), vc, vd;
   vc = f;
   vd = f.MakeVector4();

   Quaternion qa = f, qb = f.MakeQuaternion(), qc, qd;
   qc = f;
   qd = f.MakeQuaternion();

   std::cout << "va: " << va << std::endl;
   std::cout << "vb: " << vb << std::endl;
   std::cout << "vc: " << vc << std::endl;
   std::cout << "vd: " << vd << std::endl;
   std::cout << "qa: " << qa.coeffs().transpose() << std::endl;
   std::cout << "qb: " << qb.coeffs().transpose() << std::endl;
   std::cout << "qc: " << qc.coeffs().transpose() << std::endl;
   std::cout << "qd: " << qd.coeffs().transpose() << std::endl;

   return 0;
}


And finally, for reference, here's the output:

va: 2 3 4 1
vb: 2 3 4 1
vc: 2 3 4 1
vd: 2 3 4 1
qa: 2 3 4 1
qb: 2 3 4 1
qc: (4 seemingly arbitrary, junk values)
qd: 2 3 4 1


Bookmarks



Who is online

Registered users: Bing [Bot], blue_bullet, Google [Bot], rockscient, Yahoo [Bot]