如何使用递归函数(C#,D&C)避免非常大的数字的溢出乘法
Posted
技术标签:
【中文标题】如何使用递归函数(C#,D&C)避免非常大的数字的溢出乘法【英文标题】:How to avoid overflow multiplication of very big numbers with recursive function (C# , D&C) 【发布时间】:2015-06-13 13:20:08 【问题描述】:当递归函数触发并返回结果时,它会因为数据溢出而崩溃。如何使用这个 D&C 算法来避免这个问题?
static long long zarb(long a, long b, int n)
Int64 w, x, y, z;
int s;
if (a == 0 || b == 0)
return 0;
if (n <25)
return a * b;
else
s = n / 2;
long p = power(2, s);
w = a / p;
x = a % p;
y = b / p;
z = b % p;
return (zarb(w, y, n / 2) * power(2, 2 * s) + p * (zarb(w, z, n / 2) + zarb(x, y, n / 2)) + zarb(x, y, n / 2));
static long power(int x, int y)
long sum = 1;
if (y == 0)
return 0;
for (int i = 1; i <= y; i++)
sum = sum * x;
return sum;
【问题讨论】:
长数据类型溢出?你得到什么异常?是OverflowException
还是***Exception
?
那么你到底想要什么样的行为呢?防止它崩溃很容易,但你希望它如何处理?
static long long
这是 C#,不是 C。这里没有 long long
。最好不要混用Int64
和long
。它们是相同的东西,但它给读者一种不好的感觉。
@xanatos 也许是因为在他的情况下长时间溢出,OP 尝试将其写入两次以使其变得很长:p
power 在技术上是错误的。 x^0 == 1,而不是 0
【参考方案1】:
您的代码没有真正的问题,它适用于一定范围的输入。如果您需要能够输入将导致值超出 int64 范围的值,请尝试其他类型。 System.Numerics 内置于 .NET 中,并且有一个 BigInteger 类型,该类型声称“任意大整数,其值在理论上没有上限或下限”。运行这些大值输入可能需要一段时间,但应该没问题。
https://msdn.microsoft.com/en-us/library/system.numerics.biginteger%28v=vs.110%29.aspx
【讨论】:
以上是关于如何使用递归函数(C#,D&C)避免非常大的数字的溢出乘法的主要内容,如果未能解决你的问题,请参考以下文章