4

给定 2 个值,如下所示:

decimal a = 0.15m;
decimal b = 0.85m;

Where a + bwill always be 1.0m,两个值都只指定到小数点后 2 位,并且两个值都是>= 0.0m<= 1.0m

对于和的所有可能的 Decimal 值,是否保证x == total始终为x真?使用以下计算:ab

decimal x = 105.99m;
decimal total = (x * a) + (x * b);

或者是否存在x == total仅保留小数点后 2 位但不超过小数点的情况?

如果a并且b可以指定无限小数位(尽可能多Decimal),但只要a + b = 1.0m仍然成立,它会有什么不同吗?

4

2 回答 2

4

十进制以符号、整数和整数指数的形式存储为表示小数位置的数字 10。只要您的整数部分(例如 105.99 中的 105)不够大,那么 a + b 将始终等于 1。并且您的方程式 (x * a) + (x * b) 的结果将始终具有正确的四位小数。

与 float 和 double 不同,精度不会丢失到数据类型的大小(128 位)

来自 MSDN:

Decimal 值类型表示从正数 79,228,162,514,264,337,593,543,950,335 到负数 79,228,162,514,264,337,593,543,950,335 的十进制数。Decimal 值类型适用于需要大量有效整数和小数位数且无舍入错误的财务计算。Decimal 类型不会消除舍入的需要。相反,它最大限度地减少了由于四舍五入引起的错误。例如,以下代码产生的结果是 0.9999999999999999999999999999 而不是 1

decimal dividend = Decimal.One;
decimal divisor = 3;
// The following displays 0.9999999999999999999999999999 to the console
Console.WriteLine(dividend/divisor * divisor);
于 2013-01-03T13:49:08.823 回答
2

decimalCLR 中的最大精度为 29 位有效数字。当您使用这种精度时,您实际上是在谈论近似值,尤其是在进行乘法运算时,因为这需要 CLR 必须能够处理的中间结果(另请参见http://msdn.microsoft.com/en-us /library/364x0z75.aspx)。

如果 x 有 2 位有效数字,例如 a 有 20 位有效数字,则 x * a 的最小精度已经达到 22 位,中间结果可能需要更多精度。

如果 x 总是只有 2 位有效数字,并且您可以将 a 和 b 中的有效数字的数量保持足够低(例如,22 位 - 非常好并且可能远离 27 以处理舍入错误),那么我想( x * a) + (x * b) 应该是一个非常精确的计算。

最后,a + b 是否总是组成 1.0m 与 a 和 b 的个体精度无关。

于 2013-01-03T13:51:47.647 回答