【发布时间】:2020-11-10 13:26:29
【问题描述】:
我一直在使用BigNumber.js 库进行高精度算术计算。为了保持更高的精度,我使用了 Bignumber 对象的 toFixed 方法,如下所示:
(new BigNumber(6000 )).minus(9006000).div(9006000).times(4503000 ).plus(4503000 ).toFixed()
以上代码给出的结果为2999.99999999999998275。我尝试使用 decimal 数据类型在 C# 中验证此计算结果,因为小数的精度高于双精度,但结果在粒度级别上有所不同。
decimal rg1 = 6000m;
decimal lastSavedRG1 = 9006000m;
decimal lastsavedrefinedgoalMonthly1 = 4503000m;
decimal cal1 = (lastsavedrefinedgoalMonthly1 + (lastsavedrefinedgoalMonthly1 * ((rg1 - lastSavedRG1) / lastSavedRG1)));
此计算给出的值为3000.0000000000000000000001。知道为什么会有这种差异吗?
【问题讨论】:
-
BigNumber 和 C# 十进制不一样,所以它们有不同的精度也就不足为奇了
-
@Evk 差异是因为最大精度吗?但我唯一的疑问是如何验证这个大数字计算
-
例如bignumber.js有一个config,有一个选项DECIMAL_PLACES:"涉及除法的运算结果的最大小数位数,即除法、平方根和基数转换操作,和负指数的幂运算。”。默认值为 20,但您可以更改它。同时,C#十进制还有一个规则,文档说明它有28-29位精度(虽然和上面的配置不一样,但是你已经可以注意到区别了),你不能改变它。 C# 十进制不是像 bigjs 那样的任意精度数。
-
因此进行比较 - 您也需要 C# 中的任意精度数,并尽可能对它们进行相同的配置。我不知道任何具有此类属性的内置 C# 类型(有 BigInteger,但它很好,整数,没有分数),但也许有 trird 方库。或者,如果可能的话,您可以弄清楚 C# 十进制如何准确地表示一个数字并尝试在 bigjs 中做同样的事情。
-
@Evk 是的,当我将 DECIMAL_PLACES 的默认值更改为 28 时,我现在能够看到相似性。它确实将值显示为
3000.0000000000000000000000885。另外,看看你的建议,我可能会在 C# 或替代方法中寻找其他第三方库。因为它确实解决了我的目的。
标签: javascript c# arbitrary-precision bignumber.js