查看完整版本: [-- 整数快速开方算法 --]

数码之家 -> 我爱单片机 -> 整数快速开方算法 [打印本页] 登录 -> 注册 -> 回复主题 -> 发表主题

testmu 2018-01-15 12:01
赞助商链接

提个问题,单片机中怎样对数值进行求平方根?
首先想到的是使用math库的sqrt函数。
大家知道,一般做浮点数运算为了节省时间,一般把浮点数转成定点数进行计算
而sqrt函数是针对浮点数进行运行的,显然会耗费大量时间
那怎么办呢?这里提供一个以前项目中用到的算法:

unsigned int mysqrt(unsigned int x)
{
    unsigned int y;
    //初始估计值
    if(x>16384)y=192;
    else if(x>4096)y=96;
    else if(x>1024)y=48;
    else if(x>256)y=24;
    else if(x>64)y=12;
    else y=6;
    y=(y+x/y)>>1;
    y=(y+x/y)>>1;
    return y;
}
这里使用了迭代法计算,迭代次数为2,预估值会影响迭代的次数,
选择合适的预估值后,经过测试,2次已经足够了。
下面做个测试对比一下,编译环境为MPLAB X IDE,调试工具使用模拟器Sinulator,
MCU使用了PIC18F系列单片机,晶振为8M,4倍频,单指令周期为125纳秒

[attachment=11782665]

从上图可以看到,自带的sqrt函数使用了18311个指令周期,耗时超过了2毫秒
而mysqrt函数只使用了538个指令周期,耗时仅67微秒,效率相差近四十倍


[attachment=11782666]

输出结果相同,都是221.

金向维 2018-01-15 15:47
赞助商链接

不懂先收藏

testmu 2018-01-15 16:02
赞助商链接

谢谢各位打赏!
M币好难赚,到现在还是负分。

捱多年 2018-01-15 17:19
没有除法指令吧,两个除法就要几百个周期

testmu 2018-01-15 18:08
捱多年:没有除法指令吧,两个除法就要几百个周期 (2018-01-15 17:19) 

pic18确实没有 16位机好像有,不太记得了

ahyu99 2018-01-15 21:10
查表算法最快了。

la45088d1 2018-01-15 22:07
整成ASM吧,那样更快。毕竟作为数学库,不需要频繁修改。

testmu 2018-01-16 08:24
asm,不同单片机 指令和寄存器不一样,还是C通用点

ssis909 2018-01-16 10:23
有浮点就好了,FFT用的开方都是对带小数位的进行开方,结果一般都是小于1的

testmu 2018-01-16 10:38
ssis909:有浮点就好了,FFT用的开方都是对带小数位的进行开方,结果一般都是小于0的 (2018-01-16 10:23) 

可以先乘以10000取整,开方后再除以100

laodayu 2018-01-16 11:41
这个算法牛x,先收藏了,谢谢楼主!

mcu5i51 2018-01-23 10:28
很好,记得有个牛人用cmd文件写了一个整数开方,原理应该差不多,用的开方公式;


查看完整版本: [-- 整数快速开方算法 --] [-- top --]



Powered by phpwind v8.7 Code ©2003-2011 phpwind
Time 0.045945 second(s),query:5 Gzip enabled