如何用汇编或者c语言编写一个开方的子函数?

jackadandyyang 2007-04-11 02:46:10
请各位大虾们帮忙解决下,万分感谢!
...全文
1625 18 打赏 收藏 转发到动态 举报
写回复
用AI写文章
18 条回复
切换为时间正序
请发表友善的回复…
发表回复
spark_huo 2011-02-16
  • 打赏
  • 举报
回复
我想楼主需要的应该是一个做定点运算的开方以提高效率。
C原型:
#define SQRT_2 0x5A82 // 1/sqrt(2^1) = 0.70711
void Sqrt32(S32 nVal, S16 nExpInput, S16 *pnMant, S16 *pnExp)
// nVal - Q31 pnMant - Q15
{
S16 nMant, nExp;
S32 nLtmp;
int i;

if(nVal==0)
{
*pnMant = 0;
*pnExp = 0;
return;
}

nExp = Norm_32(nVal);
nVal = nVal<<nExp;
nExp = nExp + nExpInput;

nMant = 0x5e00;
for(i=0; i<5; i++)
{
nLtmp = nVal - nMant*nMant*2;
nMant += (S16) (nLtmp>>17);
}

if(nExp & 1)
{
nLtmp = nMant * SQRT_2;
nMant = (S16) (nLtmp>>15);
nExp --;
}
*pnMant = nMant;
*pnExp = nExp/2;

return;
}

其中Norm_32是32位的前导零运算。
误差很小,应该够你使用了
guanyunc 2011-02-16
  • 打赏
  • 举报
回复
;--------------------------------------------------------------------
;开方汇编子程序
;(13) 标号: SH4 功能:四字节二进制无符号数开平方(快速)
;入口条件:被开方数在R2、R3、R4、R5中。
;出口信息:平方根在R2、R3中,整数部分的位数为原数的一半,其余为小数。
;影响资源:PSW、A、B、R2~R7 堆栈需求: 2字节
;-------------------------------------------------------------------------------
SH4: MOV A,R2
ORL A,R3
ORL A,R4
ORL A,R5
JNZ SH40
RET ;被开方数为零,不必运算
SH40: MOV R7,#0 ;左规次数初始化
MOV A,R2
SH41: ANL A,#0C0H ;被开方数高字节小于40H否?
JNZ SQRH ;不小于40H,左规格化完成
MOV R6,#2 ;每左规一次,被开方数左移两位
SH42: CLR C ;被开方数左移一位
MOV A,R5
RLC A
MOV R5,A
MOV A,R4
RLC A
MOV R4,A
MOV A,R3
RLC A
MOV R3,A
MOV A,R2
RLC A
MOV R2,A
DJNZ R6,SH42 ;被开方数左移完两位
INC R7 ;左规次数加一
SJMP SH41 ;继续左规
SQRH: MOV A,R2 ;规格化后高字节按折线法分为三个区间
ADD A,#57H
JC SQR2
ADD A,#45H
JC SQR1
ADD A,#24H
MOV B,#0E3H ;第一区间的斜率
MOV R4,#80H ;第一区间的平方根基数
SJMP SQR3
SQR1: MOV B,#0B2H ;第二区间的斜率
MOV R4,#0A0H ;第二区间的平方根基数
SJMP SQR3
SQR2: MOV B,#8DH ;第三区间的斜率
MOV R4,#0D0H ;第三区间的平方根基数
SQR3: MUL AB ;与区间基点的偏移量乘区间斜率
MOV A,B
ADD A,R4 ;累加到平方根的基数上
MOV R4,A
MOV B,A
MUL AB ;求当前平方根的幂
XCH A,R3 ;求偏移量(存放在R2R3中)
CLR C
SUBB A,R3
MOV R3,A
MOV A,R2
SUBB A,B
MOV R2,A
SQR4: SETB C ;用减奇数法校正一个字节的平方根
MOV A,R4 ;当前平方根的两倍加一存入R5R6中
RLC A
MOV R6,A
CLR A
RLC A
MOV R5,A
MOV A,R3 ;偏移量小于该奇数否?
SUBB A,R6
MOV B,A
MOV A,R2
SUBB A,R5
JC SQR5 ;小于,校正结束,已达到一个字节的精度
INC R4 ;不小于,平方根加一
MOV R2,A ;保存新的偏移量
MOV R3,B
SJMP SQR4 ;继续校正
SQR5: MOV A,R4 ;将一个字节精度的根存入R2
XCH A,R2
RRC A
MOV F0,C ;保存最终偏移量的最高位
MOV A,R3
MOV R5,A ;将最终偏移量的低八位存入R5中
MOV R4,#8 ;通过(R5R6/R2)求根的低字节
SQR6: CLR C
MOV A,R3
RLC A
MOV R3,A
CLR C
MOV A,R5
SUBB A,R2
JB F0,SQR7
JC SQR8
SQR7: MOV R5,A
INC R3
SQR8: CLR C
MOV A,R5
RLC A
MOV R5,A
MOV F0,C
DJNZ R4,SQR6 ;根的第二字节计算完,在R3中
MOV A,R7 ;取原被开方数的左规次数
JZ SQRE ;未左规,开方结束
SQR9: CLR C ;按左规次数右移平方根,得到实际根
MOV A,R2
RRC A
MOV R2,A
MOV A,R3
RRC A
MOV R3,A
DJNZ R7,SQR9
SQRE: RET
foxdeng 2007-05-10
  • 打赏
  • 举报
回复
这有何难,看我的:
#include<stdio.h>
#include <math.h>
void main()
{
int x;
double squareroot;
printf("请输入要开平方的数:");
scanf("%d",&x);
squareroot=sqrt(x); /*内置函数用于求平方根*/
printf("%d的平方根为:%f",x,squareroot);
}
gcc squart.c -S squart.s
sqlnull 2007-05-10
  • 打赏
  • 举报
回复
#include<stdio.h>
#include <math.h>
void main()
{
int x;
double squareroot;
printf("请输入要开平方的数:");
scanf("%d",&x);
squareroot=sqrt(x); /*内置函数用于求平方根*/
printf("%d的平方根为:%f",x,squareroot);
}
wxspll 2007-05-09
  • 打赏
  • 举报
回复
// Carmack在QUAKE3中使用的计算平方根的函数

float CarmSqrt(float x){
union{
int intPart;
float floatPart;
} convertor;
union{
int intPart;
float floatPart;
} convertor2;
convertor.floatPart = x;
convertor2.floatPart = x;
convertor.intPart = 0x1FBCF800 + (convertor.intPart >> 1);
convertor2.intPart = 0x5f3759df - (convertor2.intPart >> 1);
return 0.5f*(convertor.floatPart + (x * convertor2.floatPart));
}
  • 打赏
  • 举报
回复
Carmack的算法真不错,比fsqrt指令快很多。
嗷嗷叫的老马 2007-05-09
  • 打赏
  • 举报
回复
UP
liangbch 2007-05-08
  • 打赏
  • 举报
回复
我曾在这个论坛回复过类似的问题,并给出完整的代码,看看这个吧:
http://readbook8.com/dev/1703/4246143.htm
paullbm 2007-04-12
  • 打赏
  • 举报
回复
開平方還是開立方?還是開更多次冪的方?
jackadandyyang 2007-04-12
  • 打赏
  • 举报
回复
都怎么了啊?都不懂的哇!55555555555
loadagain 2007-04-12
  • 打赏
  • 举报
回复
你要写这个功能先选1个合适得出开方的算法吧
gp341 2007-04-12
  • 打赏
  • 举报
回复
c里面有这个函数sqrt 还写什么
jackadandyyang 2007-04-12
  • 打赏
  • 举报
回复
怎么实现啊?望指点!等。。。!
paullbm 2007-04-12
  • 打赏
  • 举报
回复
不好意思,我把“循環‘乘’運算!!”的說法收回!!
paullbm 2007-04-12
  • 打赏
  • 举报
回复
循環‘乘’運算!!
jackadandyyang 2007-04-12
  • 打赏
  • 举报
回复
开平方哈!
大熊猫侯佩 2007-04-11
  • 打赏
  • 举报
回复
0 调用浮点指令

1 使用查找表(不精确)

2 手动编程
jackadandyyang 2007-04-11
  • 打赏
  • 举报
回复
大虾们去哪里了啊?自己来顶一下!5555

21,500

社区成员

发帖
与我相关
我的任务
社区描述
汇编语言(Assembly Language)是任何一种用于电子计算机、微处理器、微控制器或其他可编程器件的低级语言,亦称为符号语言。
社区管理员
  • 汇编语言
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧