日期:2024年5月18日标签:ComputerGraphics

四元数 #

四元数(quaternion)是另一种表示方位的方式。四元数在图形学中比较神秘,没有欧拉角简单通俗易懂。但是四元数能解决万向节锁的问题,所以本篇文章会介绍四元数这一方位表示法。

用欧拉角表示方位

四元数记法 #

四元数,从字面上看就是由四个数字组成,一个标量和一个 3D 的向量。通常将标量记为 ww,向量记为 vv 或者分开的 x,y,zx,y,z

[w,v][w,(x,y,z)][w, v] \\ [w, (x,y,z)]

复数 #

复数的基本概念 #

四元数的产生与复数有很大的关系,所以这里先复习以下复数的概念。

复数对 (a,b)(a,b) 定义了数 a+bia+biii 是所谓的虚数,满足 i2=1i^2 = -1aa实部bb虚部。任意实数 kk 都能表示成复数 (k,0)=k+0i(k,0) = k + 0i

复数支持相加、相减、相乘的运算。

(a+bi)+(c+di)=(a+c)+(b+d)i(a+bi)(c+di)=(ac)+(bd)i(a+bi)(c+di)=ac+adi+bci+bdi2=ac+(ad+bc)i+bd(1)=(acbd)+(ad+bc)i\begin{aligned} (a+bi)+(c+di)&=(a+c)+(b+d)i \\ (a+bi)-(c+di)&=(a-c)+(b-d)i \\ (a+bi)(c+di)&=ac+adi+bci+bdi^2 \\ &=ac+(ad+bc)i + bd(-1) \\ &=(ac-bd)+(ad+bc)i \end{aligned}

通过将虚部变负,还能计算复数的共轭,复数 pp 的共轭复数用 pp^* 表示。

p=a+bip=abip=a+bi \\ p^*=a-bi

复数的的记法和解释与实数的绝对值类似。

p=ppa+bi=(a+bi)(abi)=a2+b2\begin{aligned} \|p\|&=\sqrt{pp^*} \\ \|a+bi\|&=\sqrt{(a+bi)(a-bi)} \\ &=\sqrt{a^2+b^2} \end{aligned}

复数的几何意义 #

可以将复数的实部和虚部看成是平面上一个点的 x 和 y 坐标,可以认为这个平面有两个轴,实轴和虚轴,这样我们可以将复数 (x,y)(x,y) 解释为 2D 的向量。

我们可以用复数来求向量的旋转,假设向量 (x,y) 用复数表示为 x+yix + yi,将向量绕原点旋转 θ\theta 角。这里引入第二个辅助复数 q=(cosθ,sinθ)q=(\cos{\theta},\sin{\theta}),旋转后的 pp^{\prime} 计算如下:

p=x+yiq=cosθ+sinθip=pq=(x+yi)(cosθ+isinθ)=(xcosθysinθ)+(xsinθ+ycosθ)i\begin{aligned} p&=x+yi \\ q&=\cos{\theta} + \sin{\theta}i \\ p^{\prime}&=pq \\ &=(x+yi)(\cos{\theta} + i\sin{\theta}) \\ &=(x\cos{\theta} - y\sin{\theta}) + (x\sin{\theta} + y\cos{\theta})i \end{aligned}

最后的结果和利用二维旋转矩阵乘法一致。

四元数系统本质就是复数系统从 2D 到 3D 的扩展,它使用了三个虚部,i,j,ki,j,k。在左手坐标系中 i,j,ki,j,k 关系如下。

i2=j2=k2=1ij=k,ji=kjk=i,kj=iki=j,ik=ji^2=j^2=k^2=-1 \\ ij=k, ji=-k \\ jk=i,kj=-i \\ ki=j,ik=-j

一个四元数定义 [w,(x,y,z)][w, (x,y,z)] 定义了复数 w+xi+yj+zkw + xi + yj + zk

四元数表示方位 #

3D 中任意的角位移都能表示为绕单一轴的单一旋转,即用一个向量 nn 和绕该向量旋转的 θ\theta 角度表示 (n,θ)(n,\theta),这种记法称为轴角对方式。

四元数就是使用了轴角对方式,不过 nnθ\theta 不是直接存储在四元数的四个数中的,下面列出四元数中的数和 n,θn, \theta 的关系。

q=[cos(θ/2),sin(θ/2)n]=[cos(θ/2),(sin(θ/2)nx,sin(θ/2)ny,sin(θ/2)nz)]\begin{aligned} q&=[\cos{(\theta/2)}, \sin{(\theta/2)}n] \\ &=[\cos{(\theta/2)}, (\sin{(\theta/2)}n_x, \sin{(\theta/2)}n_y, \sin{(\theta/2)}n_z)] \end{aligned}

四元数运算 #

负四元数 #

将四个数都变成负数得到负四元数。

q=[w,(x,y,z)]=[w,(x,y,z)]-q=-[w, (x,y,z)] = [-w, (-x,-y,-z)]

q-qqq 表示的角位移完全相同,实际上将 θ\theta 加上 360360^\circ 之后,不会改变 qq 的角位移,但是四个分量都变成负值了,3D 中任意角位移都有两种不同的四元数表示方法。

单位四元数 #

几何上存在两个单位四元数,它们代表没有角位移:[1,0][1,\mathbf0][1,0][-1,\mathbf0]。当 θ\theta360360^\circ 的倍数时,表示没有角位移,所以 n\mathbf{n} 的值不重要。

数学上只有一个单位四元数 [1,0][1,0],用任意四元数乘以单位四元数 [1,0][1,0],结果不变。

四元数的模 #

四元数的模公式与向量类似。

q=[w,(x,y,z)]=w2+x2+y2+z2=[w,v]=w2+v2\begin{aligned} \|q\| &= \|[w, (x,y,z)]\| = \sqrt{w^2 + x^2 + y^2 + z^2} \\ &= \|[w, v]\| = \sqrt{w^2 + \|v^2\|} \end{aligned}

代入 nnθ\theta

q=w2+v2=cos2θ+sin2θn2\begin{aligned} \|q\| &= \sqrt{w^2 + v^2} \\ &= \sqrt{\cos^2{\theta} + \sin^2{\theta}n^2} \\ \end{aligned}

对于单位四元数,nn 的模长为 1。

q=w2+v2=cos2θ+sin2θn2=cos2θ+sin2θ(1)2=cos2θ+sin2θ=1\begin{aligned} \|q\| &= \sqrt{w^2 + v^2} \\ &= \sqrt{\cos^2{\theta} + \sin^2{\theta}n^2} \\ &= \sqrt{\cos^2{\theta} + \sin^2{\theta}(1)^2} \\ &= \sqrt{\cos^2{\theta} + \sin^2{\theta}} \\ &= 1 \end{aligned}

一般如果用四元数表示方位,通常使用单位四元数表示。

四元数的共轭和逆 #

四元数的共轭记作 qq^*,可通过四元数的向量部分变负得到。

q=[w,v]=[w,v]=[w,(x,y,z)]\begin{aligned} q^*&=[w, v]^* \\ &= [w, -v] \\ &= [w, (-x, -y, -z)] \end{aligned}

四元数的逆记作 q(1)q^(-1),定义为四元数的共轭除以它的模。

q(1)=qqq^(-1) = \frac{q^*}{\|q\|}

一个四元数乘以它的逆,结果为单位四元数。

四元数的乘法(叉乘) #

四元数乘法公式。

(w1+x1i+y1j+z1k)(w2+x2i+y2j+z2k)=w1w2x1x2y1y2z1z2+(w1x2+x1w2+y1z2z1z2)i+(w1y2+y1w2+z1x2x1z2)j+(w1z2+z1w2+x1y2y1x2)k\begin{aligned} & (w_1 + x_1i + y_1j + z_1k)(w_2 + x_2i + y_2j + z_2k) \\ & \begin{aligned} & = w_1w_2 - x_1x_2 - y_1y_2 - z_1z_2 \\ & + (w_1x_2 + x_1w_2 + y_1z_2 - z_1z_2)i \\ & + (w_1y_2 + y_1w_2 + z_1x_2 - x_1z_2)j \\ & + (w_1z_2 + z_1w_2 + x_1y_2 - y_1x_2)k \\ \end{aligned} \end{aligned}

由上导出了四元数乘法的标准定义。

[w1,(x1,y1,z1)][w2,(x2,y2,z2)]=[w1w2x1x2y1y2z1z2((w1x2+x1w2+y1z2z1z2)(w1y2+y1w2+z1x2x1z2)(w1z2+z1w2+x1y2y1x2))][w_1, (x_1, y_1, z_1)][w_2, (x_2, y_2, z_2)] \\ = \begin{bmatrix} w_1w_2 - x_1x_2 - y_1y_2 - z_1z_2 \\ \begin{pmatrix} (w_1x_2 + x_1w_2 + y_1z_2 - z_1z_2) \\ (w_1y_2 + y_1w_2 + z_1x_2 - x_1z_2) \\ (w_1z_2 + z_1w_2 + x_1y_2 - y_1x_2) \end{pmatrix} \end{bmatrix} [w1v1][w2v2]=[w1w2v1v2w1v2+w2v1+v2×v1]\begin{aligned} & [w_1 \quad v_1][w_2 \quad v_2] \\ & = [w_1w_2 - v_1 \cdot v_2 w_1v_2 + w_2v_1 + v_2 \times v_1] \end{aligned}

四元数叉乘满足结合律,不满足交换律。

(ab)c=a(bc)abba(ab)c = a(bc) \\ ab \neq ba

四元数乘积的模等于模的乘积,这保证了两个单位四元数相乘的结果还是单位四元数。

q1q2=q1q2\|q_1q_2\| = \|q_1\|\|q_2\|

四元数乘积的逆等于各个四元数的逆以相反的顺序相乘。

(ab)1=a1b1(ab)^{-1} = a^{-1}b^{-1}

四元数乘法的一个重要的几何意义,可以用于 3D 点的旋转。设旋转四元数 qq 的形式为 [cosθ/2,nsinθ/2][\cos{\theta/2}, \mathbf{n}\sin{\theta/2}]n\mathbf{n} 为旋转轴,θ\theta 为旋转角,则执行下面的乘法可以使 3D 点 ppn\mathbf{n} 旋转 θ\theta 角。

p=qpq1p^{\prime} = qpq^{-1}

将点 pp 用一个四元数 aa 旋转后,再用 bb 旋转:

p=b(apa1)b1=(ba)p(a1b1)=(ba)p(ba)1\begin{aligned} p^{\prime} &= b(apa^{-1})b^{-1} \\ &= (ba)p(a^{-1}b^{-1}) \\ &= (ba)p(ba)^{-1} \end{aligned}

所以先进行 a 旋转,再进行 b 旋转,等价于执行乘积 ba 代表的单一旋转。四元数的乘法能连接多次旋转,这与矩阵的乘法效果一致。

四元数的“差” #

利用四元数的乘法和逆能够计算四元数的“差”,“差”被定义为一个方位到另一个方位的角位移。即给定方位 a 和 b 就能够计算出从 a 旋转到 b 的角位移 d,用四元数表示,即 ad=bad=b

要想计算 dd,就可以使等式两边同时除以 a,但是四元数不能进行除法,但是可以乘以它的逆:

a1(ad)=a1ba^{-1}(ad) = a^{-1}b

应用乘法的结合律得到

(a1a)d=a1b[10]d=a1bd=a1b\begin{aligned} (a^{-1}a)d &= a^{-1}b \\ [1 \quad \mathbf{0}]d&=a^{-1}b \\ d&=a^{-1}b \end{aligned}

四元数点乘 #

四元数点乘与向量的点乘非常类似,而且结果也是个标量。

q1q2=[w1v1][w2v2]=w1w2+v1v2=w1w2+x1x2+y1y2+z1z2\begin{aligned} q_1 \cdot q_2 &= [w_1 \quad v_1][w_2 \quad v_2] \\ & = w_1w_2 + v_1 \cdot v_2 \\ &= w_1w_2 + x_1x_2 + y_1y_2 + z_1z_2 \end{aligned}

四元数点乘的几何解释类似于向量点乘的几何解释,四元数点乘 aba \cdot b 的绝对值越大,aabb 代表的角位移越相似。

四元数求幂 #

四元数能作为底数,记作 qtq^t,四元数求幂与实数求幂类似。四元数 qq 代表一个角位移, 1/3 这个角位移的四元数记作 q^{1/3}。例如 qq 代表绕 x 轴顺时针旋转 3030^\circ,则 q2q^2 代表绕 x 轴顺时针旋转 6060^\circq1/3q^{-1/3} 代表绕 x 轴逆时针旋转 1010^\circ

(完)

目录