大数除法

示例:

99999999999999999999(20位) / 33333333333333333333(20位) = 3...0

ps: 3...0:表示商为3,余数为0。

思想:这里主要是用大数快速减法来模拟大数除法运算,我们用例子来说明。

先看一简单例子:12 / 3 = 4

化成减法,就是这样。

12 - 3 = 9

9 - 3 = 6

6 - 3 = 3

3 - 3 = 0

这里进行了4次减法运算才使结果小于3,所以商就4.

然后,看一个复杂的例子:12345 / 91 = 135...60

12345           (由于div1[pos]<div2[0],此时pos=0,所以++pos,91从div1第二位开始匹配)

  91                (进行一次运算,相当于进行了100次减91运算,所以商要加上100。)

-----------          ps:由于开辟了一个长度为len1的数组sum[5]储存商。sum[0]sum[1]sum[2]sum[3]sum[4]  。

03245             所以,如果要加上100,则进行++sum[2]操作。

    91              

-----------

02335

    91

-----------

01425

    91

-----------

00515           我们用zero标记div1高位上最后一个无效0的位置,比如此时zero = 1。

      91

-----------

00424             我们用pos标记div2与div1首位匹配的位置,比如此时pos = 3。

      91

-----------

00333

      91

-----------

00242

      91

-----------

00151

      91

-----------

00060        (此时得到的60小于90,减法结束,同时余数就是60)

/*
	Title:大数除法
	Author:Dojking
*/
#include <iostream>
#include <string>
#include <math.h>
using namespace std;

void BigDiv(string div1, string div2)
{
	int i, j, pos = 0, zero = -1, len1, len2;

	len1 = div1.size()-1;
	len2 = div2.size()-1;
	int *sum = new int[len1+2];      /*开辟空间*/
	for (i = 0; i <= len1+1; ++i)    /*初始化为0*/
		sum[i] = 0;
	while ((&div1[zero+1] >= div2 && len1-zero-1 == len2) || (len1-zero-1 > len2))/*直到被除数小于除数*/
	{
		pos = zero+1;                /*zero表示div1高位最后一个无效0的位置*/
		if (div1[pos] < div2[0])     /*高位匹配位置*/
			++pos;
		for (i = len2+pos, j = len2; j >= 0; --i, --j)/*大数相减*/
		{
			if (div1[i] < div2[j] || div1[i] == 'f')  /*需要借位:在字符串中f表示-1*/
			{
				if (div1[i-1] != 0)    /*上一位可以借位*/
					div1[i-1] -= 1;
				else                   /*上一位为0*/
					div1[i-1] -= 'f';
				if (div1[i] == 'f')    /*运算:本位为f*/
					div1[i] = (-1) + 10 - (div2[j]-'0') + '0';/*将f用-1代替*/
				else
					div1[i] = (div1[i]-'0') + 10 - (div2[j]-'0') + '0';/*借位:即+10*/
			}
			else
			{
				div1[i] = (div1[i]-'0') - (div2[j]-'0') + '0';/*不需借位:直接运算*/
			}
		}
		while (div1[zero+1] == '0' && (zero+1 < len1))/*找到div1高位最后一个无效0的位置*/
			++zero;
		++sum[len2+pos];/*统计结果:做减法的次数就是商*/ 
	}
	for (i = 0; i <= len1; ++i)/*进位*/
	{
		if (sum[i] >= 10)
		{
			sum[i-1] = sum[i]/10;
			sum[i] %= 10;
		}
	}
	i = 0;
	while ((sum[i] == 0) && (i < len1))/*舍掉高位无效0,防止全部为0情况bug*/
		++i;
	for ( ; i <= len1; ++i)    /*输出商*/
		cout<<sum[i];
	cout<<"..."<<&div1[zero+1]<<endl;/*输出余数*/
}

int main()
{
	string div1, div2;

	cin>>div1>>div2;
	BigDiv(div1, div2); /*大数除法*/

	return 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、付费专栏及课程。

余额充值