精度计算(大数方面)

来源:互联网 发布:联想网络同传 编辑:程序博客网 时间:2024/05/11 21:38

1.  大数阶乘

返回:n!的位数

结果:a[10000]记录n!的数据

#include<stdio.h>

#include<math.h>

int factorial(intn);

int main()

{

    int re;

    re=factorial(1000); //测试用的

    printf("\n%d\n",re);

    return 0;

}

int factorial(int n)

{

    long a[10000];//int类型也可以

    int i,j,l,c,w,m=0;

    a[0]=1;

    for(i=1;i<=n;i++)//i小于等于n,注意边界问题

    {

        c=0;

        for(j=0;j<=m;j++)

        {

            a[j]=a[j]*i+c;

            c=a[j]/10000;//取4位以上的数据

            a[j]%=10000;

        }

        if(c>0)

        {

            m++;

            a[m]=c;

        }

    }

    w=m*4+log10(a[m])+1;//math里面的函数

    printf("\n%ld",a[m]);

    for(i=m-1;i>=0;i--)

        printf("%4.4ld",a[i]);//如果a[i]不够4位 在前面自动补零

    return w;

}

 

2.  乘法——(大数乘小数)

c[]:被乘数,用字符串表示,位数不限

t[]:存储结果,用字符串表示

m:乘数,可以限定在任何数范围内,不过要修改下面一处代码

#include<stdio.h>

#include<string.h>

void mult(charc[],char t[],int m);

int main()

{

    charc[]="123456789";//测试数据

    char t[20];

    int m=6;

    mult(c,t,m);

    int i=0;

    while(*(t+i))

    {

        printf("%c",*(t+i));

        i++;

    }

    return 0;

}

void mult(charc[],char t[],int m)

{

    int i,l,k,flag,add=0;

    int s[100];//char类型也可以

    l=strlen(c);//被乘数的长度,string.h头文件里面有,计算字符串长度

    for(i=0;i<l;i++)

        s[l-i-1]=c[i]-'0';//把字符转换为数字 低位字符转换到数字数组高位

    for(i=0;i<l;i++)

    {

        k=s[i]*m+add;//add是进位标志

        if(k>=10)//小数是10以内,要扩大可以可这里

        {

            s[i]=k%10;

            add=k/10;

            flag=1;

        }

        else

        {

            s[i]=k;

            flag=0;

            add=0;

        }

       

    }

    if(flag)//最高位数乘积有进位,长度l要注意边界问题

    {

        l=i+1;

        s[i]=add;

    }

    else

        l=i;

    for(i=0;i<l;i++)

        t[l-i-1]=s[i]+'0';

    t[l]='\0'; 

}

3.  大数乘大数

// a:乘数

// b:被乘数

// s: 结果

#include<stdio.h>

#include<string.h>

void mult(char a[],char b[],char s[]);

int main()

{

chara[]="0";

charb[]="10";

char s[65];

int i=0;

mult(a,b,s);

while(*(s+i))

{

     printf("%c",*(s+i));

     i++;

}

return 0;

}

void mult(char a[],char b[],char s[])

{

int i,j,alen,blen;

intres[65][65]={0};//必须初始化为全零,下面是上三角形式的把位乘积相加

intk=0,sum=0,flag=0;

char result[65];

alen=strlen(a);//被乘数长度

blen=strlen(b);//乘数长度

//将a每位数与b每位数相乘 保存在res

for(i=0;i<alen;i++)

     for(j=0;j<blen;j++)

         res[i][j]=(a[i]-'0')*(b[j]-'0');

for(i=alen-1; i>= 0; i--)//计算res右下半个三角数的和

{

     for(j =blen-1; j >= 0; j--)

         sum=sum+res[i+blen-j-1][j];//sum存储着几个数的和

     result[k]=sum%10;

     k++;

     sum/=10;//存储进位信息

}

for(i=blen-2;i>=0;i--)//计算另一半的三角的和

{

     for(j=0;j<=i;j++)

         sum+=res[i-j][j];

    result[k]=sum%10;

     k++;

     sum/=10;

}

if(sum) //最后一步有进位,要注意处理

{

     result[k]=sum;

     k++;

}

for(i=0;i<k;i++)

     result[i]+='0';//转换为字符acsii

for(i=k-1;i>=0;i--)

     s[i]=result[k-i-1];

s[k]='\0';//方便以后处理,打印,哨兵的意思

while(1)//处理乘数或是被乘数是0,并让结果与a长度相同

{

     if(strlen(s)!=strlen(a)&&s[0]=='0')

         strcpy(s,s+1);

     else

         break;

}

 

}

0 0
原创粉丝点击