大数除法(求商和取余)

感觉除法是四则运算中最难的
大数除法的运算可以分为两种:求商和取余
有两个大整数a和b,当a=b时,a/b=1,余数是0。(a!=0,b!=0);
当a>b时,a/b>=1,余数需要通过计算求得;
当a<b时,a/b=0,余数为a。
比较难求的就是a>b时。
其实基本的思想就是反复做减法,看看从被除数里最多能减去多少个除数,商就是多少。一个一个减显然太慢,如何减得更快一些呢?
以28536 除以23 为例来看一下:开始商为0。
先减去23 的1000 倍,就是23000,发现够减1 次,余下5536,于是商的值就增加1000;
然后用5536减去2300,发现够减2 次,余下936,于是商的值增加200,即1200;
再用936 减去230,够减4 次,余下16,于是商值增加40,即1240。
最后,发现余下的数比23小,即为余数,即28536 / 23 得1240余16。
其实这就是我们平时的列竖式。
代码:

#include<stdio.h>  
#include<string.h>  
char a[100],b[100];//用两个字符串用来输入两个大数   
int x[100],y[100],z[100];//被除数  除数  商  余数   
int digit;//大数的位数   
void sub(int x[],int y[],int len1,int len2)//大数减法   
{  
    int i;  
    for(i=0;i<len1;i++)  
    {  
        if(x[i]<y[i])  
        {  
            x[i]=x[i]+10-y[i];  
            x[i+1]--;  
        }  
        else  
            x[i]=x[i]-y[i];  
    }  
    for(i=len1-1;i>=0;i--)//判断减法结束之后,被除数的位数   
    {  
        if(x[i])  
        {   
            digit=i+1;  
            break;           
        }   
    }  
}  
int judge(int x[],int y[],int len1,int len2)  
{  
    int i;  
    if(len1<len2)        //若除数的位数大,返回-1 
        return -1;  
    if(len1==len2)//若两个数位数相等   
    {  
        for(i=len1-1;i>=0;i--)  
        {  
            if(x[i]==y[i])//对应位的数相等   
                continue;  
            if(x[i]>y[i])//被除数 大于 除数,返回值为1   
                return 1;  
            if(x[i]<y[i])//被除数 小于 除数,返回值为-1   
                return -1;  
        }  
        return 0;//被除数 等于 除数,返回值为0   
    }     
}  
int main()  
{  
    int i,j=0,k=0,temp;  
    int len1,len2,len;//len两个大数位数的差值     
    while(~scanf("%s %s",a,b))  
    {  
        len1=strlen(a);//被除数位数  
        len2=strlen(b);//除数位数  
        for(i=len1-1,j=0;i>=0;i--)//将字符串中各个元素倒序储存在数组中   
            x[j++]=a[i]-'0';   
           
        for(i=len2-1,k=0;i>=0;i--)  
            y[k++]=b[i]-'0';              
        if(len1<len2)//当被除数位数 小于 除数位数时   
        {  
            printf("商是:0\n");  
            printf("余数是:");  
            puts(a);   
        }  
        else //当被除数位数 大于或者 除数位数时  
        {  
            len=len1-len2;//两个大数位数的差值  
            for(i=len1-1;i>=0;i--)//将除数后补零,使得两个大数位数相同。被除数:4541543329 除数:98745,加零后:9874500000   
            {  
                if(i>=len)  
                    y[i]=y[i-len];  
                else  
                    y[i]=0;  
            }  
            len2=len1;//将两个大数数位相同         
            digit=len1; //将原被除数位数赋值给digit   
            for(j=0;j<=len;j++)  
            {  
                z[len-j]=0;  
                while(((temp=judge(x,y,len1,len2))>=0)&&digit>=k)//被除数大于等于除数 ,原被除数位数大于等于除数位数 
                {     
                    sub(x,y,len1,len2); //大数减法函数                  
                    z[len-j]++;//储存商的每一位  
                    len1=digit;//重新修改被除数的长度  
                    if(len1<len2&&y[len2-1]==0)        
                        len2=len1;//将len1长度赋给len2;                        
                }  
                if(temp<0)//若被除数 小于 除数,除数减小一位。例如:被除数:4541543329 除数:(原)98745,(加零后)9874500000,后退一位后:0987450000   
                {  
                    for(i=1;i<len2;i++)  
                        y[i-1]=y[i];  
                    y[i-1]=0;  
                    if(len1<len2)   
                        len2--;                                           
                }  
            }  
            printf("商是:");  
            for(i=len;i>0;i--)//去掉前缀0   
            {  
                if(z[i])  
                    break;  
            }  
            for(;i>=0;i--)  
                printf("%d",z[i]);  
            printf("\n");  
            printf("余数是:");  
            for(i=len1;i>0;i--)  
            {  
                if(x[i])  
                    break;  
            }  
            for(;i>=0;i--)  
                printf("%d",x[i]);  
            printf("\n");  
        }  
    }  
    return 0;  
}

  • 0
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Python中,当我们对两个整数进行除法时,结果将是一个浮点数。但是,如果我们想要得到整数除法的结果,我们可以使用“//”运算符。此外,我们可以使用“%”运算符来获得余数。但是,当我们处理大数除法时,我们需要注意一些问题。 一种解决大数除法的方法是使用Python的Decimal模块。Decimal模块提供了高精度的十进制算术运算。我们可以使用Decimal模块中的divide()函数来执行大数除法。下面是一个示例代码: ```python from decimal import * a = Decimal('123456789012345678901234567890') b = Decimal('987654321098765432109876543210') c = a / b print(c) ``` 输出结果为: ``` 0.1249999999999999999999999999 ``` 另一种解决大数除法的方法是使用Python的long division算法。这种算法可以手动模拟除法过程,从而避免使用浮点数。下面是一个示例代码: ```python a = '123456789012345678901234567890' b = '987654321098765432109876543210' # 将字符串转换为数字列表 a = [int(x) for x in a] b = [int(x) for x in b] # 执行长除法 q = [] r = [] for d in a: r.append(d) s = 0 while len(r) >= len(b): t = b.copy() m = len(r) - len(t) t = [0] * m + t s += 1 for i in range(len(t)): r[i] -= t[i] if r[i] < 0: r[i] += 10 r[i+1] -= 1 while len(r) > 0 and r[-1] == 0: r.pop() q.append(s) # 将数字列表转换为字符串 q = ''.join([str(x) for x in q]) r = ''.join([str(x) for x in r]) print(q) print(r) ``` 输出结果为: ``` 0 123456789012345678901234567890 ```

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值