最美情侣中文字幕电影,在线麻豆精品传媒,在线网站高清黄,久久黄色视频

歡迎光臨散文網(wǎng) 會員登陸 & 注冊

實驗:CORDIC計算三角函數(shù)【C】

2023-02-06 16:08 作者:扎之克  | 我要投稿

簡介:

? ? ? ? CORDIC(Coordinate Rotation Digital Computer)算法即坐標旋轉數(shù)字計算方法,是J.D.Volder1于1959年首次提出,主要用于三角函數(shù)、雙曲線、指數(shù)、對數(shù)的計算。該算法通過基本的加和移位運算代替乘法運算,使得矢量的旋轉和定向的計算不再需要三角函數(shù)、乘法、開方、反三角、指數(shù)等函數(shù)。(百度百科)

? ? ? ? CORDIC算法使用更適合計算機的運算來計算旋轉,通過矢量旋轉就可以得到三角函數(shù)、反三角函數(shù)的值,通過雙曲旋轉能計算雙曲三角函數(shù)、開方、指數(shù)等,它的應用非常廣泛,這里就只提關于Cordic計算三角函數(shù)的部分。


簡單提一下原理:

首先推一下旋轉的迭代公式,這里用復數(shù)乘法推。

如圖,矢量(x0,y0)逆時針旋轉θ角度后得到(x1,y1),

那么有 ,

根據(jù)公式

?以及 復數(shù)乘法加法的運算律得到

所以有

提出cos(θ)或者sin(θ)就得到了矢量旋轉的迭代公式

這里需要乘tan(θ),試著把它變成移位運算,我們知道右移n位相當于乘以2^(-n),這里用excel計算一下對應的角度值θ。

表中的角度值θ有兩個良好的性質:

第一:將θ從0到15求和得到99.882°,這說明從0到15迭代的旋轉范圍在[-99.882°,99.882°]。

第二:

,這是一個很好的性質,表格中上下兩個角度的比值都接近0.5,如果輸入角在[-90°,90°]間,旋轉角度可以類似二分法那樣去靠近輸入角度。

現(xiàn)在可以用右移來代替乘tan(θ),還剩一個乘cos(θ)需要處理,

把cos(θ)去掉,與真正的旋轉相比少了一個拉伸,這也被稱為偽旋轉,如果迭代次數(shù)固定,那么拉伸系數(shù)也是固定的。

固定迭代16次,求出每次的拉伸系數(shù)再乘起來就得到了最終的拉伸系數(shù)K,在excel中算出K=0.607252935。

(順便提一下,提出sin的公式的k=4.56846E-37,這非常小,寫代碼的話不好搞。)

得到k的值后,就能計算向量旋轉的近似值了,比如求向量(1,0)逆時針旋轉θ度后的向量,可以用(1,0)偽旋轉迭代16次后乘以k得到近似值,優(yōu)化一下,k和(1,0)都是固定值,把k*(1,0)先算得到新的初值,那就變成:用(k,0)偽旋轉迭代16次。

得到旋轉后的向量再根據(jù)下面的公式就能求三角函數(shù)了。

測試代碼(部分,完整的在https://blog.csdn.net/qq_39892910/article/details/128895614?spm=1001.2014.3001.5502):

int?Ang[16]={4500000,2656505,1403624,712502,357633,178991,89517,44761,22381,11191,5595,2798,1399,699,350,175};

int cos_core(int a)

{

???? char i;

???? int x=30363,y=0,temp;//18次迭代,先連續(xù)2次45°旋轉作為90°旋轉,輸入角度范圍擴大至[-189.8812173,189.8812173]

???? if(a>=18988122||a<=-18988122)

???? ????return 0;???

???? if(a>=0)

???? {

???????? temp=x-y;

???????? y+=x;

???????? x=temp;

???????? temp=x-y;

???????? y+=x;

???????? x=temp;

???????? a-=9000000;

???? }

???? else if(a<0)

???? {

???????? temp=x+y;

???????? y-=x;

???????? x=temp;

???????? temp=x+y;

???????? y-=x;

???????? x=temp;

???????? a+=9000000;

???? }

???? for(i=0;i<16;i++)

???? {

???????? if(a>=0)

???????? {

???????????? temp=x-(y>>i);

???????????? y+=(x>>i);

???????????? x=temp;

???????????? a-=Ang[i]; ??

???????? }

???????? else if(a<0)

???????? {

???????????? temp=x+(y>>i);

???????????? y-=(x>>i);

???????????? x=temp;

???????????? a+=Ang[i]; ?

???????? }

???? }

???? return x;

}

int atan2_core(int y,int x)

{

???? char i;

???? int temp,a;

???? a=0;

???? if(y<0)

???? {

???????? temp=x-y;

???????? y+=x;

???????? x=temp;

???????? temp=x-y;

???????? y+=x;

???????? x=temp;

???????? a-=9000000;

???? }

???? else if(y>0)

???? {

???????? temp=x+y;

???????? y-=x;

???????? x=temp;

???????? temp=x+y;

???????? y-=x;

???????? x=temp;

???????? a+=9000000;

???? }

???? else

???? {

???????? if (x<0)

???????? return 18000000;

???????? else //兩個情況,但atan2(0.0,0.0)返回0.0,所以直接返回0

???????? return 0;

???? }

???? for(i=0;i<16;i++)

???? {

???????? if(y<0)

???????? {

???????????? temp=x-(y>>i);

???????????? y+=(x>>i);

???????????? x=temp;

???????????? a-=Ang[i]; ??

???????? }

???????? else if(y>0)

???????? {

???????????? temp=x+(y>>i);

???????????? y-=(x>>i);

???????????? x=temp;

???????????? a+=Ang[i]; ?

???????? }

???????? else

???????? ? return a;

???? }

???? return a;

}


輸出:

? ? ? ? 時間:我在單片機平臺上復制了一份一樣的代碼,PC的輸出結果與單片機的輸出結果截然不同。

PC輸出:

單片機(STM32F103)輸出:


經(jīng)過對比:單片機上CORDIC比math的三角函數(shù)快很多,PC上math的三角函數(shù)比CORDIC快很多。兩個平臺在許多方面有巨大差異,不清楚是什么原因導致了這種情況。


誤差:

(這里的誤差是以math的三角函數(shù)輸出值為參考,兩者相減的絕對值作為誤差)

在這方面,PC與單片機的輸出結果相同:

反正切atan2:


余弦:

觀察到cos(180°)、cos(0°)等的輸出超出了范圍,得限制一下輸出,其他看起來感覺還湊合,我會在單片機平臺上使用它。

如果按照上面代碼來運行,旋轉角度不會與輸入角度相等。在我這個思路中,初值固定,所以迭代次數(shù)也固定,就算旋轉角度早已與輸入重合,它也要走完剩下的。當然這是有解決辦法的,也有很多地方可以優(yōu)化,我這寫的比較粗糙,我自己湊合著用。

實驗:CORDIC計算三角函數(shù)【C】的評論 (共 條)

分享到微博請遵守國家法律
黔东| 牡丹江市| 扎囊县| 屯留县| 海林市| 武乡县| 滨州市| 齐齐哈尔市| 紫金县| 射阳县| 北安市| 宿州市| 海安县| 盐池县| 商水县| 噶尔县| 确山县| 新泰市| 广平县| 兰西县| 宣城市| 潞西市| 扬州市| 岳池县| 河源市| 龙泉市| 肥东县| 衡阳市| 监利县| 平阴县| 且末县| 保亭| 丰县| 青州市| 德清县| 苍梧县| 泾源县| 城口县| 平果县| 临潭县| 邢台县|