风花雪月 发表于 2005-10-4 10:18

[转帖]大数运算的乘除算法

#include &lt;stdio.h&gt; <BR>#include &lt;stdlib.h&gt; <BR>#include &lt;string.h&gt; <BR>#include &lt;ctype.h&gt; <BR><BR>int cchkdig(char *r) <BR>{ <BR>int i=0;<BR>while(r!='\0') <BR>{ <BR>if(isdigit(r)==0) <BR>return (0); <BR>} <BR>return (1);<BR>} <BR><BR>//去掉整数串表示前面多余的零,最后结果为空串时置为"0" <BR>void cdel0(char *r) <BR>{<BR>unsigned int lr;<BR>int i=0, j; <BR>lr=strlen(r);<BR>while(r=='0') <BR>++i;<BR>if(i&gt;0) <BR>{<BR>for(j=0; j&lt;lr-i; ++j)<BR>r=r;<BR>for(j=lr-i; j&lt;lr; ++j) <BR>{<BR>r='\0'; <BR>}<BR><BR>}<BR><BR>if(r=='\0')<BR>{<BR>r='0';<BR>} <BR>} <BR><BR>int scmp(char *r, char *u) <BR>{ <BR>unsigned int lr, lu; <BR>cdel0(r);<BR>cdel0(u); <BR><BR>lr=strlen(r); <BR>lu=strlen(u); <BR><BR>if(lr&gt;lu) <BR>{<BR>return 1;<BR>}<BR>else if (lr&lt;lu) <BR>{<BR>return -1;<BR>}<BR>return (strcmp(r, u)); <BR><BR>}//end scmp() <BR><BR>//两个串表示数的减法 <BR>char *ssub(char *r, char *u) <BR>{<BR>unsigned int i,lr, lu, lp,c=0;<BR>char h,hc; <BR>char *p;<BR>if(scmp(r, u)&lt;0) <BR>return NULL; <BR>lr=strlen(r); <BR>lu=strlen(u); <BR>p=(char *)malloc((unsigned int)(lr+1)*sizeof(char)); <BR>for(i=0; i&lt;lu; ++i) <BR>{<BR>h=r-u-c; <BR>if(h&lt;0) <BR>{<BR>c=1; <BR>h=h+10;<BR>} <BR>else <BR>c=0; <BR>p=h+'0';<BR>hc=h+'0';<BR>} <BR>for (i=lu; i&lt;lr; ++i) <BR>{ <BR>h=r-'0'-c;<BR>if(h&lt;0) <BR>{<BR>c=1; <BR>h=h+10; <BR>} <BR>else <BR>c=0; <BR>p='0'+h; <BR>hc='0'+h;<BR>}<BR>p='\0';<BR>lp=i-1;<BR><BR>while(p=='0'&amp;&amp;lp!=0)<BR>{<BR>p='\0';<BR>lp--; <BR>}<BR><BR><BR>for(i=0; i&lt;(lp+1)/2; ++i) <BR>{ <BR>hc=p; <BR>p=p; <BR>p=hc; <BR>} <BR>return (p); <BR>}//end ssub() <BR><BR>//两个串表示数的加法 <BR>char *sadd(char *r, char *u) <BR>{ <BR>unsigned int lr, lu, lp; <BR>int i, h, c=0; <BR>char hc, *p; <BR>lr=strlen(r); <BR>lu=strlen(u); <BR>if(lu&gt;lr) <BR>{ <BR>p=r; <BR>r=u; <BR>u=p; <BR>h=lr; <BR>lr=lu; <BR>lu=h; <BR>} <BR>p=(char *)malloc((unsigned int)(lr+2)*sizeof(char));<BR>for(i=0; i&lt;lu; ++i) <BR>{ <BR>h=r-'0'+u-'0'+c; <BR>if(h&gt;9) <BR>{ <BR>c=1;<BR>h=h-10; <BR>} <BR>else <BR>c=0;<BR>p=h+'0';<BR>} <BR>for(i=lu; i&lt;lr; ++i) <BR>{ <BR>h=r-'0'+c; <BR>if(h&gt;9) <BR>{ <BR>c=1; <BR>h=h-10; <BR>} <BR>else <BR>c=0;<BR>p='0'+h;<BR>} <BR>if(c&gt;0) <BR>{ <BR>p=c+'0'; <BR>lp=i; <BR>} <BR>else <BR>lp=i-1;<BR>for(i=lp+1; i&lt;lr+2; ++i) <BR>p='\0'; <BR>for(i=0; i&lt;(lp+1)/2; ++i) <BR>{ <BR>hc=p; <BR>p=p; <BR>p=hc; <BR>} <BR>return (p); <BR>}//end sadd() <BR><BR>//两个串表示数的乘法 <BR>char *smut(char *r, char *u) <BR>{ <BR>unsigned int lr, lu, lp; <BR>int i, j, c, h; <BR>char *p; <BR>lr=strlen(r); <BR>lu=strlen(u); <BR>p=(char *)malloc((unsigned int)(lr+lu+1)*sizeof(char)); <BR>for(i=0; i&lt;lr+lu; ++i) <BR>p='0'; <BR>p='\0'; <BR><BR>for(i=lr-1; i&gt;=0; --i) <BR>{ <BR>c=0;<BR>for(j=lu-1; j&gt;=0; --j) <BR>{ <BR>lp=i+j+1;<BR>h=(r-'0')*(u-'0')+p-'0'+c;<BR>c=h/10;<BR>h=h%10;<BR>p=h+'0';<BR>} <BR>if(c&gt;0)p=c+'0';<BR>} <BR><BR>cdel0(p);<BR>return p;<BR>}//end smut() <BR><BR>//两个串表示数的除法,结果精确到小数点后第n位 <BR>char *sdivf(char *u, char *v, int n) <BR>{ <BR>char *p, *f, *r,*q;<BR>unsigned int i, lu, lv, lr,iw, c, h;<BR>intkh, j;<BR>lu=strlen(u);<BR>lv=strlen(v);<BR>f=(char *)malloc((unsigned int)(lu+n+3)*sizeof(char)); <BR>q=(char *)malloc(sizeof(char)); <BR>for(i=0; i&lt;lu+n+3; ++i) <BR>f='\0'; <BR>r=(char *)malloc((unsigned int)(lv+2)*sizeof(char)); <BR>for(i=0; i&lt;lv+2; ++i) <BR>r='\0'; <BR>for(iw=0; iw&lt;lu+n+2; ++iw) <BR>{ <BR>if(iw&lt;lu) <BR>{ <BR>cdel0(r); <BR>lr=strlen(r); <BR>r=u; <BR>r='\0';<BR>} <BR><BR>else if(iw&gt;lu) <BR>{ <BR>cdel0(r);<BR>q='0';<BR>if(scmp(r, q)==0)<BR>{<BR>break; <BR>}<BR>lr=strlen(r); <BR>r='0';<BR>r='\0'; <BR>} <BR><BR>else <BR>{ <BR>f='.'; <BR>continue;<BR>}<BR><BR>kh=0; <BR>while(scmp(r, v)&gt;=0) <BR>{ <BR>p=r;<BR>r=ssub(p, v); <BR>++kh; <BR>} <BR>f=kh+'0'; <BR>} <BR>if(iw==lu+n+2) <BR>{ <BR>if(f&gt;='5') <BR>{ <BR>f='\0';<BR>c=1;<BR>for(j=lu+n; j&gt;=0; --j) <BR>{ <BR>if(c==0) <BR>{<BR>break;<BR>}<BR>if(f=='.')<BR>{<BR>continue; <BR>}<BR>h=f-'0'+c;<BR>if(h&gt;9) <BR>{ <BR>h=h-10; <BR>c=1; <BR>} <BR>else <BR>c='\0';<BR>f=h+'0'; <BR>} <BR>} <BR>else <BR>f='\0'; <BR><BR>} <BR>free(r); <BR>free(p);<BR>q=NULL;<BR>free(q);<BR>cdel0(f);<BR>return(f);<BR>}//end sdivf() <BR><BR>//两个串表示数的除法,结果分别用整商与余数表示 <BR>char *sdivkr(char *u, char *v, char **rout) <BR>{ <BR>char*f, *r;<BR>unsigned int i, lu, lv, lr, iw;<BR>intkh;<BR>lu=strlen(u);<BR>lv=strlen(v);<BR><BR>f=(char *)malloc((unsigned int)(lu+1)*sizeof(char)); <BR>for(i=0; i&lt;lu+1; ++i) f='\0'; <BR>r=(char *)malloc((unsigned int)(lv+2)*sizeof(char)); <BR>for(i=0; i&lt;lv+2; ++i) r='\0'; <BR><BR>for(iw=0; iw&lt;lu; ++iw) <BR>{ <BR>cdel0(r); <BR>lr=strlen(r); <BR>r=u; <BR>r='\0'; <BR>kh=0; <BR>while(scmp(r, v)&gt;=0) <BR>{ <BR>r=ssub(r, v); <BR>++kh; <BR>} <BR>f=kh+'0'; <BR>} <BR>cdel0(r);<BR>*rout=r;<BR>cdel0(f); <BR>    return(f);<BR><BR>}//end *sdivkr() <BR><BR>//调用上述函数实现两任意长正整数任意指定精度的算术计算器程序 <BR>void main(int argc, char *argv[]) <BR>{ <BR>char *p, *r;<BR>int n;<BR>if(argc!=4)<BR>{ <BR>if(argc!=3)<BR>printf("\n&gt;&gt;\"order n1 op n2\" or n ! "); <BR>exit(0); <BR>} <BR>cdel0(argv);<BR>if(cchkdig(argv)==0)<BR>{ <BR>printf("Input data error, Input again!"); <BR>exit(0); <BR>} <BR>cdel0(argv);<BR>if(cchkdig(argv)==0) <BR>{ <BR>printf("Input data error, Input again!"); <BR>exit(0); <BR>} <BR><BR>if(strcmp(argv, "+")==0) <BR>{ <BR>printf("%s", p=sadd(argv, argv)); <BR>free(p); <BR>} <BR><BR>else if(strcmp(argv, "-")==0) <BR>{ <BR>printf("%s", p=ssub(argv, argv)); <BR>free(p); <BR>} <BR><BR>else if(strcmp(argv, "*")==0) <BR>{ <BR>printf("%s", p=smut(argv, argv)); <BR>free(p); <BR>} <BR><BR>else if(argv=='/' &amp;&amp; strlen(argv)==1) <BR>{ <BR>if(argv=='0')<BR>{<BR>printf("error!devided by zero!!\n");<BR>exit(0);<BR>}<BR>p=sdivkr(argv, argv, &amp;r);<BR>printf("k=%s r=%s", p, r);<BR>free(p); <BR>free(r);<BR>} <BR><BR>else if(argv=='/'&amp;&amp;strlen(argv)&gt;1) <BR>{ <BR>if(argv=='0')<BR>{<BR>printf("error!devided by zero!!\n");<BR>exit(0);<BR>}<BR><BR>argv='\0';<BR>cdel0(argv);<BR>if(cchkdig(argv)==0) <BR>{ <BR>printf("Input data error, Input again!"); <BR>exit (0); <BR>} <BR>n=atoi(argv);<BR>printf("%s", p=sdivf(argv, argv, n));<BR>free(p);<BR>} <BR><BR><BR>}
页: [1]
查看完整版本: [转帖]大数运算的乘除算法