提问人:Rúben Dias 提问时间:1/24/2023 更新时间:1/25/2023 访问量:55
Java 中的精确混合比较 BigInteger 和 double
Exact mixed comparison BigInteger and double in Java
问:
刚刚注意到 Python 和 JavaScript 有确切的比较。 Python 中的示例:
>>> 2**1023+1 > 8.98846567431158E307
True
>>> 2**1023-1 < 8.98846567431158E307
True
和 JavaScript:
> 2n**1023n+1n > 8.98846567431158E307
true
> 2n**1023n-1n < 8.98846567431158E307
true
任何类似的东西都可用于 Java,除了将两个参数转换为 大十进制?
答:
初步答案,即口头解决方案草图:
我对可以转换的解决方案持怀疑态度 转换为 BigDecimal,因为此转换会导致 基数从 base=2 移动到 base=10。一旦 作为 Java 双精度浮点值的指数 与二进制精度不同,这会导致额外的数字和冗长 pow() 操作,可以通过检查来验证 一些开源的BigDecimal(double) 构造函数实现。
可以通过 Double.doubleToRawLongBits(d) 获取尾数。 如果 Java 双精度浮点值不是次正态值 所有需要做的是(原始和DOUBLE_SNIF_MASK)+ (DOUBLE_SNIF_MASK+1) 其中 0x000fffffffffL 这意味着 整数 Java 原语类型 long 应该足以 携带尾数。现在的挑战是进行比较 还要考虑浮点数的指数。
但我必须承认,我还没有时间工作 出一些 Java 代码。我也想到了一些 使用另一个的 bigLength() 进行优化 参数,在此设置中为 BigInteger。 使用 bitLength() 将加快比较速度。 一个简单的启发式方法可以实现一个快速路径,这样 尾数可以忽略不计。已经是指数 的 double 和 BigInteger 的 bitLength() 为比较结果提供足够的信息。
只要我有时间并运行原型,我可能会 在此处发布一些 Java 代码片段。但也许有人 已经面对问题了。我的一般假设是,快速或 即使是超快速的例程也是可能的。但我没有 很多时间在互联网上搜索并找到一个 实现,这就是为什么我把问题推迟到 堆栈溢出,也许其他人也有同样的情况 问题和/或可能指向一个完整的解决方案?
评论
double
BigInteger
BigDecimal
BigInteger
BigDecimal
BigDecimal
BigInteger
double
BigInteger
BigDecimal
double
BigInteger