旋转模式用来解决三角函数,实现极坐标到直角坐标的转换,基础理论请参考Cordic算法——圆周系统之旋转模式。那么,向量模式则用来解决反三角函数的问题,体现的应用主要是直角坐标向极坐标转换,即已知一点的直角坐标(x,y),求其极坐标(α,γ),实际上是求arctan(y/x)。

旋转模式下,每次迭代使z趋近于α(α-z趋近于0),而向量模式下,则使y趋近于0,这一点很好理解,即从坐标位置,旋转到x正半轴,一共旋转了多少角度,则该角度即为α,从而知道了极角。

如图所示,在单位圆上,向量OP与X轴的正半轴夹角为α,故P点的坐标可表示为

根据开头描述,我们需要转动向量OP,先顺时针旋转θ角至向量OQ,Q点的坐标可表示为

这里定义θ为目标旋转角度。根据三角函数公式可将上式展开为

现在已经有点 Cordic 算法的样子了,但是我们看到每次旋转都要计算 4 次浮点数的乘法运算,运算量还是太大了。还需要进一步的改进,改进的切入点当然还是坐标变换的过程。

将式(1.1)代入到式(1.3)中可得

用矩阵形式表示为:

旋转了i次以后,可以得到:

最终需将y_Q_i+1转为0,先按45°的二分法查找来解释过程,用C语言描述过程为:

#include <stdio.h>
#include <stdlib.h> double cordic_v(double x, double y); int main(viod)
{
double alfa = cordic_v(120.0,200.0); //直角坐标(x,y)
printf("\n 极角为 = %f \n",alfa);
return 0;
}
double cordic_v(double x, double y)
{
const double sine[] = {0.7071067811865,0.3826834323651,0.1950903220161,
0.09801714032956,0.04906767432742,0.02454122852291,0.01227153828572,
0.006135884649154,0.003067956762966,0.001533980186285,
7.669903187427045e-4,3.834951875713956e-4,1.917475973107033e-4,
9.587379909597735e-5,4.793689960306688e-5,2.396844980841822e-5
}; const double cosine[] = {0.7071067811865,0.9238795325113,0.9807852804032,0.9951847266722,
0.9987954562052,0.9996988186962,0.9999247018391,0.9999811752826,0.9999952938096,
0.9999988234517,0.9999997058629,0.9999999264657,0.9999999816164,0.9999999954041,
0.999999998851,0.9999999997128
};
int i = 0;
double x_new, y_new;
double angleSum = 0.0;
double angle = 45.0; //第一次旋转角度为45°
for( i=0; i<15;i++)
{
if(y > 0)
{
x_new = x * cosine[i] + y * sine[i];
y_new = y * cosine[i] - x * sine[i];
x = x_new;
y = y_new;
angleSum += angle;
} else
{
x_new = x * cosine[i] - y * sine[i];
y_new = y * cosine[i] + x * sine[i];
x = x_new;
y = y_new;
angleSum -= angle;
}
printf("旋转次数: i = %2d 旋转角度 = %10f, 累计旋转角度 = %10f\n", i+1, angle,angleSum );
angle /= 2;
}
return angleSum;
}

经过旋转模式的推导,向量模式的伪旋转公式,可表示为

C语言描述过程,如下:

#include <stdio.h>
#include <stdlib.h>
#include <math.h> double cordic_v(double x, double y);
double r = 0.0; //定义一个模长全局变量 int main(viod)
{
double alfa = cordic_v(120.0,200.0); //直角坐标(x,y)
printf("\n极角 = %5f, 模长 = %5f\n",alfa,r);
return 0;
}
double cordic_v(double x, double y)
{
const double theta[] = { 45.0, 26.56505118, 14.03624347, 7.125016349,
3.576334375, 1.789910608, 0.8951737102, 0.4476141709,
0.2238105004, 0.1119056771, 0.05595289189, 0.02797645262,
0.01398822714, 0.006994113675, 0.003497056851, 0.001748528427
}; //旋转角度
int i = 0;
double x_new, y_new;
double angleSum = 0.0;
r = sqrt(x*x+y*y);
for( i=0; i<16;i++)
{
if(y > 0)
{
x_new = x + y/(1<<i);
y_new = y - x/(1<<i);
x = x_new;
y = y_new;
angleSum += theta[i];
} else
{
x_new = x - y/(1<<i);
y_new = y + x/(1<<i);
x = x_new;
y = y_new;
angleSum -= theta[i];
}
printf("旋转次数: i = %2d 旋转角度 = %10f, 累计旋转角度 = %10f, y = %5f\n", i+1,theta[i],angleSum,y );
}
return angleSum;
}

同样,向量模式的cordic算法适用于第一、四象限的坐标变换,在第二、三象限的坐标需要进行预处理。

参考

FPGA算法学习(1) -- Cordic(圆周系统之向量模式)的更多相关文章

  1. FPGA算法学习(1) -- Cordic(Verilog实现)

    上两篇博文Cordic算法--圆周系统之旋转模式.Cordic算法--圆周系统之向量模式做了理论分析和实现,但是所用到的变量依然是浮点型,而cordic真正的用处是基于FPGA等只能处理定点的平台.只 ...

  2. FPGA算法学习(1) -- Cordic(圆周系统之旋转模式)

    三角函数的计算是个复杂的主题,有计算机之前,人们通常通过查找三角函数表来计算任意角度的三角函数的值.这种表格在人们刚刚产生三角函数的概念的时候就已经有了,它们通常是通过从已知值(比如sin(π/2)= ...

  3. Cordic算法——圆周系统之向量模式

    旋转模式用来解决三角函数,实现极坐标到直角坐标的转换,基础理论请参考Cordic算法--圆周系统之旋转模式.那么,向量模式则用来解决反三角函数的问题,体现的应用主要是直角坐标向极坐标转换,即已知一点的 ...

  4. Cordic算法——圆周系统之旋转模式

    三角函数的计算是个复杂的主题,有计算机之前,人们通常通过查找三角函数表来计算任意角度的三角函数的值.这种表格在人们刚刚产生三角函数的概念的时候就已经有了,它们通常是通过从已知值(比如sin(π/2)= ...

  5. python学习之算法、自定义模块、系统标准模块(上)

    算法.自定义模块.系统标准模块(time .datetime .random .OS .sys .hashlib .json和pickle) 一:算法回顾: 冒泡算法,也叫冒泡排序,其特点如下: 1. ...

  6. Python之路,Day21 - 常用算法学习

    Python之路,Day21 - 常用算法学习   本节内容 算法定义 时间复杂度 空间复杂度 常用算法实例 1.算法定义 算法(Algorithm)是指解题方案的准确而完整的描述,是一系列解决问题的 ...

  7. 《如何学习基于ARM嵌入式系统》笔记整理

    author:Peong time:20190603 如何学习基于ARM嵌入式系统 一.嵌入式系统的概念 从硬件上讲,将外围器件,与CPU集成在一起. 从操作系统上讲,定制符合要求的系统内核 从应用上 ...

  8. paxos算法学习总结

    核心思想 分布式系统架构下如何让整体尽快达成一致观点,也就是多个不同观点收敛到一个观点的过程. 难点 可能会发生少数节点故障,但绝不是大面积故障,不然系统也没法正常工作. 由于存在单点故障,因此不可能 ...

  9. 某科学的PID算法学习笔记

    最近,在某社团的要求下,自学了PID算法.学完后,深切地感受到PID算法之强大.PID算法应用广泛,比如加热器.平衡车.无人机等等,是自动控制理论中比较容易理解但十分重要的算法. 下面是博主学习过程中 ...

随机推荐

  1. ubuntu 18 下配置 WebStorm 编译 sass

    ubuntu 18 下配置 WebStorm 编译 scss 标签(空格分隔): IDE 安装Ruby: sudo apt-get install ruby ruby -v ruby 2.5.1p57 ...

  2. codis学习

    一.codis-proxy 结构 1.Topology 2.Slots 3.ServerGroup 4.Server   二.codis-proxy 启动过程   1.初始化ProxyInfo Id ...

  3. 抓取android系统日志_记录一次定位app闪退故障

    在测试android客户端兼容性时,发现app闪退,上海的小伙伴需要闪退时的系统日志:故把快生锈的adb知识拿出来show一把: 1.下载adb工具包(adb的全称为Android Debug Bri ...

  4. bzoj3816 矩阵变换

    Description 给出一个 N 行 M 列的矩阵A, 保证满足以下性质: M>N. 矩阵中每个数都是 [0,N] 中的自然数. 每行中, [1,N] 中每个自然数都恰好出现一次.这意味着每 ...

  5. 【[NOI2006]最大获利】

    题目 并不知到为什么这道题讲了这么久 我们发现这道题就是最小割的板子啊,完全可以套上文理分科的板子 把每个机器和\(T\)连边,容量为\(p_i\),这些\(p_i\)并不计入总贡献 对于每一个要求我 ...

  6. 2018.11.19 Struts2中Action类的书写方式

    方式1: 方式2: 方式3

  7. 【题解】洛谷 P1525 关押罪犯

    题目 https://www.luogu.org/problemnew/show/P1525 思路 把所有边sort一遍从大到小排列 运用并查集思想敌人的敌人就是朋友 从最大边开始查找连着的两个罪犯 ...

  8. POJ 3616 Milking Time(加掩饰的LIS)

    传送门: http://poj.org/problem?id=3616 Milking Time Time Limit: 1000MS   Memory Limit: 65536K Total Sub ...

  9. Python 学习笔记(七)Python字符串(一)

    字符串 字符串或串(String)是由数字.字母.下划线组成的一串字符,用双引号或单引号包裹的为字符串 1 >>> "hello world" 2 'hello ...

  10. Oracle 11g行字段拼接WMSYS.WM_CONCAT问题Not A LOB

    Oracle 11g行字段拼接WMSYS.WM_CONCAT问题Not A LOB 一.问题出现 项目中的某个查询需要将表中某个字段不重复地拼接起来,百度得到该函数WMSYS.WM_CONCAT(字段 ...