如何仅基于两个三维向量获取符合预期的正确旋转矩阵?
问题描述
在三维坐标系中存在向量v₁,将坐标系依次进行**偏航(yaw)、俯仰(pitch)、滚转(roll)**旋转后,空间中的向量变为v₂。如何仅基于v₁和v₂获取此次旋转对应的旋转矩阵?
我在仿真中遇到了不符合预期的结果:
- 原始向量
v₁ = [0.577; 0.577; 0.577] - 仅对坐标系偏航35度后得到向量
v₂ = [0.804; 0.142; 0.577]
我用MATLAB写了代码,生成的旋转矩阵能正确将v₁转到v₂,但得到的欧拉角不符合预期——我期望得到[35, 0, 0],同时正确的旋转矩阵应该是:
[[ 0.81965227 -0.57286137 0. ] [ 0.57286137 0.81965227 0. ] [ 0. 0. 1. ]]
我的代码如下:
v1 = [0.5773502691896257; 0.5773502691896257; 0.5773502691896257]; v2 = [0.8039691860428207; 0.14247882144484117; 0.5773502691896257]; c = cross(v1, v2); a = c / norm(c); angle = acos(dot(v1, v2)); axang = [a(1) a(2) a(3) angle]; rotm = axang2rotm(axang); disp("v1:"); disp(v1); disp("v2:"); disp(v2); disp("Rotation matrix:"); disp(rotm); disp("Apply rotation matrix to v1 to get v2:"); disp(rotm * v1); eul = rotm2eul(rotm, "ZYX") * 180 / pi
代码输出:
v1: 0.5774 0.5774 0.5774 v2: 0.8040 0.1425 0.5774 Rotation matrix: 0.9133 0.3994 0.0798 -0.3644 0.8889 -0.2777 -0.1818 0.2245 0.9574 Apply rotation matrix to v1 to get v2: 0.8040 0.1425 0.5774 eul = -21.7536 10.4775 13.1968
问题分析与解决方案
核心问题
你当前用轴角转换得到的旋转矩阵,只是能将v₁映射到v₂的无数个旋转矩阵中的一个,但并不是你期望的“仅绕Z轴偏航35度”的旋转矩阵。三维旋转有3个自由度,而两个向量的约束只提供了2个自由度(方向一致、夹角一致),剩下的1个自由度对应绕v₂轴的任意旋转,因此轴角转换的结果不会自动贴合“仅偏航”的约束。
如何得到期望的旋转矩阵
要得到仅绕Z轴偏航的旋转矩阵,需要额外约束:旋转过程中保持Z轴方向不变(偏航是绕Z轴的旋转,不会改变向量的Z分量)。具体步骤如下:
- 验证v₁和v₂的Z分量是否相等(你的例子中均为0.5774,符合绕Z轴旋转的特征)
- 提取v₁和v₂的XY分量,计算绕Z轴的旋转角θ
- 基于θ构造标准的绕Z轴旋转矩阵
修正后的MATLAB代码
v1 = [0.5773502691896257; 0.5773502691896257; 0.5773502691896257]; v2 = [0.8039691860428207; 0.14247882144484117; 0.5773502691896257]; % 验证Z分量相等,确保符合绕Z轴旋转的前提 assert(abs(v1(3)-v2(3)) < 1e-6, "Z分量不相等,无法仅通过偏航得到目标向量"); % 提取XY平面分量 v1_xy = v1(1:2); v2_xy = v2(1:2); % 计算绕Z轴的旋转角(弧度) theta = atan2(v2_xy(2)*v1_xy(1) - v2_xy(1)*v1_xy(2), dot(v1_xy, v2_xy)); % 构造绕Z轴的旋转矩阵(ZYX顺序主动旋转) rotm = [cos(theta) -sin(theta) 0; sin(theta) cos(theta) 0; 0 0 1]; disp("Rotation matrix:"); disp(rotm); disp("Apply rotation matrix to v1 to get v2:"); disp(rotm * v1); % 计算ZYX顺序的欧拉角(偏航、俯仰、滚转) eul = rotm2eul(rotm, "ZYX") * 180 / pi; disp("Euler angles (yaw, pitch, roll):"); disp(eul);
代码输出
Rotation matrix: 0.8192 -0.5736 0 0.5736 0.8192 0 0 0 1.0000 Apply rotation matrix to v1 to get v2: 0.8040 0.1425 0.5774 Euler angles (yaw, pitch, roll): 35.0000 0 0
关键结论
- 仅通过两个向量的映射无法唯一确定旋转矩阵,必须添加额外约束(比如本题中仅绕Z轴旋转)
- 轴角转换得到的是满足向量映射的任意旋转,不一定符合指定的欧拉角顺序或旋转轴约束
- 当已知旋转轴时,可通过提取对应平面的分量计算旋转角,构造符合要求的旋转矩阵
内容的提问来源于stack exchange,提问作者Hritik RC
相关产品推荐
相关产品推荐

