C++ Eigen 库中旋转向量、旋转矩阵、欧拉角、四元数的定义及互相转换

Eigen库旋转变换
本文介绍使用Eigen库进行旋转变换的方法,包括旋转向量、欧拉角、旋转矩阵及四元数的定义与相互转换。文章分享了相关博客资源,方便读者深入学习。

今天看师兄写的使用力反馈设备操作机械臂的代码,里边涉及到了Eigen 库中的旋转变换,表征旋转变换的有旋转向量Eigen::AngleAxisd、欧拉角Eigen::Vector3d、旋转矩阵Eigen::Matrix3d以及四元数Eigen::Quaterniond,关于它们的定义以及相互转换,我在网上找到了两篇非常不错的博客,写的这么好,咱就没有必要再整理一遍了(其实是懒),存了存了,写在这里也分享给需要的朋友~

Eigen库使用教程之旋转矩阵,旋转向量和四元数的初始化和相互转换的实现

eigen 中四元数、欧拉角、旋转矩阵、旋转向量

<think> 我们被要求使用Eigen旋转矩阵转换四元数根据引用[2]和引用[3],有两种主要方法: 引用[2]指出: 旋转矩阵四元数有两种方式: Eigen::Quaterniond quaternion(rotation_matrix); 或者 Eigen::Quaterniond quaternion; quaternion = rotation_matrix; 引用[3]也给出了一个例子: q_odom_curr_now = Eigen::Quaterniond ( rotation_matrix ); 因此,我们可以使用构造函数直接初始化,或者使用赋值运算符。 步骤: 1. 确保有一个3x3的旋转矩阵Eigen::Matrix3d类型)。 2. 使用该旋转矩阵来构造一个Quaterniond对象,或者将旋转矩阵赋值给一个四元数。 注意:引用[1]提到,Eigen四元数的类型是Eigen::Quaterniond。 另外,根据引用[3]的示例,转换后的四元数可以直接用于表示旋转。 重要提示:旋转矩阵必须是正交的,且行列式为1(即旋转矩阵属于SO(3))。在转换前,如果旋转矩阵是通过数值计算得到的,可能存在数值误差,建议进行正交化处理,但Eigen转换函数内部会处理这些误差(通过归一化等)。 下面给出具体代码示例: </think> ### 使用 Eigen 旋转矩阵转换四元数的方法 在 Eigen 中,旋转矩阵(`Eigen::Matrix3d`)转换四元数(`Eigen::Quaterniond`)主要有三种等效方法: #### 🔧 方法 1:直接构造函数 ```cpp Eigen::Matrix3d rotation_matrix = ...; // 你的旋转矩阵 Eigen::Quaterniond quaternion(rotation_matrix); // 直接构造 ``` #### 🔄 方法 2:赋值运算符 ```cpp Eigen::Quaterniond quaternion; quaternion = rotation_matrix; // 通过赋值转换 ``` #### ️ 方法 3:使用 `fromRotationMatrix()` 方法 ```cpp Eigen::Quaterniond quaternion; quaternion = Eigen::Quaterniond::FromRotationMatrix(rotation_matrix); ``` #### 💻 完整示例代码 ```cpp #include <Eigen/Dense> #include <Eigen/Geometry> #include <iostream> int main() { // 创建绕Z轴旋转90°的旋转矩阵 Eigen::Matrix3d R; R << 0, -1, 0, 1, 0, 0, 0, 0, 1; // 方法1: 直接构造 Eigen::Quaterniond q1(R); // 方法2: 赋值运算符 Eigen::Quaterniond q2; q2 = R; // 方法3: FromRotationMatrix Eigen::Quaterniond q3 = Eigen::Quaterniond::FromRotationMatrix(R); // 验证结果(应相同) std::cout << "q1 coefficients: " << q1.coeffs().transpose() << std::endl; std::cout << "q2 coefficients: " << q2.coeffs().transpose() << std::endl; std::cout << "q3 coefficients: " << q3.coeffs().transpose() << std::endl; // 验证旋转效果 Eigen::Vector3d v(1, 0, 0); std::cout << "Original vector: " << v.transpose() << std::endl; std::cout << "Rotated vector: " << (q1 * v).transpose() << std::endl; return 0; } ``` #### ⚠️ 重要注意事项 1. **存储顺序**: Eigen 四元数内部存储为 $(x,y,z,w)$,但构造函数使用 $(w,x,y,z)$。使用 `.coeffs()` 方法获取向量表示时返回顺序为 $[x,y,z,w]$ 2. **归一化处理**: 转换过程会自动归一化四元数满足 $|q| = 1$,但建议检查: ```cpp assert(std::abs(q1.norm() - 1.0) < 1e-6); ``` 3. **旋转矩阵要求**: - 必须是正交矩阵($R^T R = I$) - 行列式必须为 1($\det(R) = 1$) - 建议使用 `rotation_matrix.isUnitary()` 验证 4. **数值稳定性**: 对于接近奇异的旋转矩阵,使用角轴(`AngleAxisd`)作为中间表示更稳定: ```cpp Eigen::Quaterniond q(Eigen::AngleAxisd(rotation_matrix)); ``` #### 🌟 应用场景 这种方法在机器人学(如 ROS 中的 TF 变换)、计算机视觉(相机位姿估计)和三维图形学(模型旋转)中广泛应用,因为: 1. 四元数插值(`slerp`)比矩阵更平滑 2. 避免欧拉角的万向节死锁问题 3. 更高效的旋转组合($q_{total} = q_1 \otimes q_2$)[^1][^2][^3]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值