国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 學院 > 開發設計 > 正文

為什么要使用四元數

2019-11-08 03:21:33
字體:
來源:轉載
供稿:網友

為 了回答這個問題,先來看看一般關于旋轉(面向)的描述方法-歐拉描述法。它使用最簡單的x,y,z值來分別表示在x,y,z軸上的旋轉角度,其取值為 0-360(或者0-2pi),一般使用roll,pitch,yaw來表示這些分量的旋轉值。需要注意的是,這里的旋轉是針對世界坐標系說的,這意味著 第一次的旋轉不會影響第二、三次的轉軸,簡單的說,三角度系統無法表現任意軸的旋轉,只要一開始旋轉,物體本身就失去了任意軸的自主性,這也就導致了萬向 軸鎖(Gimbal Lock)的問題。鑒于歐拉角插值動畫時有錯誤,因此不能使用歐拉角的方式來進行球面方式插值,相應地,就可以采用四元數的方式來解決這個問題。如果系統還是使用歐拉角表示,要先轉換為四元數,然后再進行插值,再轉換回來歐拉角表示。

四元數的應用范圍很廣泛,它的定義如下:

四元數是簡單的超復數。 復數是由實數加上虛數單位 i 組成,其中i^2 = -1。 相似地,四元數都是由實數加上三個虛數單位 i、j、k 組成,而且它們有如下的關系: i^2 = j^2 = k^2 = -1, i^0 = j^0 = k^0 = 1 , 每個四元數都是 1、i、j 和 k 的線性組合,即是四元數一般可表示為a + bk+ cj + di,其中a、b、c 、d是實數。對于i、j、k本身的幾何意義可以理解為一種旋轉,其中i旋轉代表X軸與Y軸相交平面中X軸正向向Y軸正向的旋轉,j旋轉代表Z軸與X軸相交平面中Z軸正向向X軸正向的旋轉,k旋轉代表Y軸與Z軸相交平面中Y軸正向向Z軸正向的旋轉,-i、-j、-k分別代表i、j、k旋轉的反向旋轉。

ij = k, ji = -k, jk = i, kj = -i, ki =j, ik = -j

四元數的虛部可以使用qv, 實部使用qw,那么就可表示為(qv, qw)的形式。

1.四元數和軸-角對  繞軸n旋轉θ角:n是一個向量,根據左手或右手法則定義旋轉的正方向, θ角表示旋轉的量。  那么表示這個旋轉的四元數為:

2. 四元數的模

代入軸-角對的公式求模。 n為單位向量,最后可以得到四元數的模為1.稱為單位四元數。

3. 四元數的共軛

四元數和它的共軛代表相反的角位移,因為相當于旋轉軸反向。

4. 四元數乘法(叉乘)

5. 優點

通俗的講,一個四元數(Quaternion)描述了一個旋轉軸和一個旋轉角度。這個旋轉軸和這個角度可以通過 Quaternion::ToAngleAxis轉換得到。當然也可以隨意指定一個角度一個旋轉軸來構造一個Quaternion。這個角度是相對于單位四元數而言的,也可以說是相對于物體的初始方向而言的。當用一個四元數乘以一個向量時,實際上就是讓該向量圍繞著這個四元數所描述的旋轉軸,轉動這個四元數所描述的角度而得到的向量。有多種方式可表示旋轉,如 axis/angle、歐拉角(Euler angles)、矩陣(matrix)、四元組等。 相對于其它方法,四元組有其本身的優點:    四元數不會有歐拉角存在的 gimbal lock 問題    四元數由4個數組成,旋轉矩陣需要9個數    兩個四元數之間更容易插值    四元數、矩陣在多次運算后會積攢誤差,需要分別對其做規范化(normalize)和正交化(orthogonalize),對四元數規范化更容易    與旋轉矩陣類似,兩個四元組相乘可表示兩次旋轉

6. 四元數轉換為矩陣

7. 四元數插值

代碼:

quat slerp(quat qa, quat qb, double t) {	// quaternion to return	quat qm = new quat();	// Calculate angle between them.	double cosHalfTheta = qa.w * qb.w + qa.x * qb.x + qa.y * qb.y + qa.z * qb.z;	// if qa=qb or qa=-qb then theta = 0 and we can return qa	if (abs(cosHalfTheta) >= 1.0){		qm.w = qa.w;qm.x = qa.x;qm.y = qa.y;qm.z = qa.z;		return qm;	}	// Calculate temporary values.	double halfTheta = acos(cosHalfTheta);	double sinHalfTheta = sqrt(1.0 - cosHalfTheta*cosHalfTheta);	// if theta = 180 degrees then result is not fully defined	// we could rotate around any axis normal to qa or qb	if (fabs(sinHalfTheta) < 0.001){ // fabs is floating point absolute		qm.w = (qa.w * 0.5 + qb.w * 0.5);		qm.x = (qa.x * 0.5 + qb.x * 0.5);		qm.y = (qa.y * 0.5 + qb.y * 0.5);		qm.z = (qa.z * 0.5 + qb.z * 0.5);		return qm;	}	double ratioA = sin((1 - t) * halfTheta) / sinHalfTheta;	double ratioB = sin(t * halfTheta) / sinHalfTheta; 	//calculate Quaternion.	qm.w = (qa.w * ratioA + qb.w * ratioB);	qm.x = (qa.x * ratioA + qb.x * ratioB);	qm.y = (qa.y * ratioA + qb.y * ratioB);	qm.z = (qa.z * ratioA + qb.z * ratioB);	return qm;}更多,請參考:

http://www.cnblogs.com/mengdd/archive/2013/08/05/3238223.htmlhttp://blog.csdn.net/candycat1992/article/details/41254799http://blog.csdn.net/jin_syuct/article/details/49785541

1. C++標準模板庫從入門到精通 

http://edu.csdn.net/course/detail/3324

2.跟老菜鳥學C++

http://edu.csdn.net/course/detail/2901

3. 跟老菜鳥學python

http://edu.csdn.net/course/detail/2592

4. 在VC2015里學會使用tinyxml

http://edu.csdn.net/course/detail/2590

5. 在Windows下SVN的版本管理與實戰 

 http://edu.csdn.net/course/detail/2579

6.Visual Studio 2015開發C++程序的基本使用 

http://edu.csdn.net/course/detail/2570

7.在VC2015里使用PRotobuf協議

http://edu.csdn.net/course/detail/2582

8.在VC2015里學會使用MySQL數據庫

http://edu.csdn.net/course/detail/2672


發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 汉沽区| 宜黄县| 尼玛县| 阜康市| 海兴县| 南开区| 北辰区| 广水市| 尤溪县| 泰安市| 新和县| 叶城县| 灌阳县| 定南县| 蛟河市| 大连市| 黄冈市| 阿拉善盟| 靖安县| 新巴尔虎右旗| 温州市| 涟水县| 井陉县| 荣昌县| 花莲市| 祁连县| 辉县市| 介休市| 大埔区| 丹阳市| 阆中市| 渑池县| 五家渠市| 公安县| 桂平市| 乌审旗| 南和县| 大姚县| 台北县| 清流县| 晋江市|