仅出于乐趣,并证明它可以完成,我完成了一个AVR组装例程,以24位(3字节)的形式计算sin(x)结果,但有一点错误。输入角度以度为单位,带有一个十进制数字,仅对于第一象限为000到900(0〜90.0)。它使用不到210条AVR指令,平均运行时间为212微秒,范围从211us(角度= 001)到213us(角度= 899)。
考虑到AVR微控制器,没有浮点,消除了所有可能的划分,花了几天的时间来完成所有工作,超过10天(空闲时间)才考虑了最佳的计算算法。要花费更多时间来为整数设置正确的升压值,要具有良好的精度,需要将1e-8的值升压为2 ^ 28或更大的二进制整数。一旦发现所有精度和舍入误差元,将其计算分辨率提高2 ^ 8或2 ^ 16,就可以达到最佳结果。我首先在Excel上模拟了所有计算,同时将所有值都设为Int(x)或Round(x,0)来表示AVR核心处理。
例如,在算法中,角度必须以弧度为单位,输入以度为单位,以方便用户使用。要将度数转换为弧度,平凡的公式是rad = degrees * PI / 180,这看起来很容易,但事实并非如此,PI是一个无限数-如果使用很少的数字,则会在输出中产生错误,除以180需要AVR位操作,因为它没有除法指令,并且除此以外,由于涉及远远低于整数1的数字,结果将需要浮点运算。例如,1°(度)的Radian为0.017453293。由于PI和180是常数,为什么不为了简单的乘法而反转呢?PI / 180 = 0.017453293,乘以2 ^ 32,得出的常数为74961320(0x0477D1A8),然后将此数字乘以角度(以度为单位),假设900代表90°,然后将其右移4位(÷16),以获得4216574250(0xFB53D12A),即90°的弧度(具有2 ^ 28的扩展),适合4个字节,不作任何除法(除4右移)。在某种程度上,这种技巧所包含的误差小于2 ^ -27。
因此,所有进一步的计算都需要记住它要高出2 ^ 28并加以注意。您需要将运行中的结果除以16、256甚至65536,只是为了避免它使用不必要的,无法帮助解决的增长饥饿字节。这是一项艰巨的工作,只是在每个计算结果中找到最少的位数,使结果精度保持在24位左右。在Excel流程中,按尝试/错误方式使用高位或低位进行多次计算中的每一项,在结果中观察错误位的总数,该图显示0-90°,其中宏运行代码900次,十分之一度。这种“可视化” Excel方法是我创建的工具,它为代码的每个部分找到了最佳解决方案,这大有帮助。
例如,将此特殊的计算结果13248737.51舍入为13248738.或仅丢失“ 0.51”小数,它将对所有900个输入角度(00.1〜90.0)测试的最终结果精度产生多大影响?
在每次计算中,我都能使动物保持在32位(4字节)之内,并最终获得了魔术,从而在结果的23位之内获得了精度。当检查结果的整个3个字节时,误差为±1 LSB,未解决。
用户可以根据自己的精度要求从结果中抓取一个,两个或三个字节。当然,如果仅一个字节就足够了,我建议使用一个256字节的sin表,并使用AVR'LPM'指令来抓取它。
一旦我使Excel序列运行平稳,整洁,从Excel到AVR程序集的最终翻译就用了不到2个小时,通常,您应该首先考虑更多,而以后再减少工作。
那时,我可以进一步压缩并减少寄存器的使用。实际的(不是最终的)代码使用大约205条指令(〜410字节),平均以212us运行sin(x)计算,时钟为16MHz。以该速度,它每秒可以计算4700+ sin(x)。并不重要,但是它可以运行高达4700Hz的精确正弦波,具有23位的精度和分辨率,而无需任何查找表。
基本算法基于针对sin(x)的泰勒级数,但进行了很多修改,以适应AVR微控制器和精度的要求。
即使使用2700字节的表(900个条目* 3字节)也会吸引速度,这有什么乐趣或学习经验呢?当然,也考虑使用CORDIC方法,也许稍后,这里的重点是将Taylor挤入AVR岩心并从干燥的岩石中取水。
我想知道Arduino“ sin(78.9°)”是否可以在不到212us的时间内以23位的精度运行处理(C ++),并且所需的代码小于205条指令。可能是C ++使用CORDIC。Arduino草图可以导入汇编代码。
在此处发布代码没有任何意义,稍后我将编辑此帖子以包括指向该链接的Web链接,可能在我的博客上,网址为。该博客主要使用葡萄牙语。
这项没有钱的爱好很有趣,在没有除法指令的情况下,仅以8x8位进行乘法运算,就将16VIPS的AVR引擎的极限提高到16MHz。它允许计算sin(x),cos(x)[= sin(900-x)]和tan(x)[= sin(x)/ sin(900-x)]。
最重要的是,这有助于保持我63岁的大脑的光彩和油脂。当青少年说“老年人”对技术一无所知时,我回答“再想一想,您认为谁创造了今天享受的一切的基础?”。
干杯