java 如何确定double的最大精度

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/36344758/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-11-03 01:18:42  来源:igfitidea点击:

How to determine the max precision for double

javafloating-pointdoubleprecision

提问by Shivam Sinha

I am trying to determine what the maximum precision for a double is. In the comments for the accepted answer in this link Retain precision with double in Java@PeterLawrey states max precision in 15.

我试图确定双精度的最大精度是多少。在此链接中接受的答案的评论中,在 Java 中保留双精度精度@PeterLawrey 指出最大精度为 15。

How do you determine this ?

你如何确定这一点?

采纳答案by user207421

@PeterLawrey states max precision in 15.

@PeterLawrey 声明了 15 的最大精度。

That's actually not what he stated at all. What he stated was:

这其实根本不是他说的。他说的是:

double has 15 decimal places of accuracy

double 有 15 个小数位的精度

and he is wrong. They have 15 decimal digitsof accuracy.

他错了。它们具有 15 位十进制数字的准确度。

The number of decimal digits in any number is given by its log to the base 10. 15 is the floor value of log10(253-1), where 53 is the number of bits of mantissa (including the implied bit), as described in the Javadoc and IEEE 754, and 253-1 is therefore the maximum possible mantissa value. The actual value is 15.954589770191003298111788092734 to the limits of the Windows calculator.

任何数中的十进制位数由其以 10 为底的对数给出。 15 是对数10(2 53-1) 的下限值,其中 53 是尾数的位数(包括隐含位),如在 Javadoc 和 IEEE 754 中描述,因此2 53-1 是最大可能的尾数值。实际值是 15.954589770191003298111788092734 到 Windows 计算器的限制。

He is quite wrong to describe it as 'decimal places of accuracy'. A doublehas 15 decimal digitsof accuracy if they are all before the decimal point.For numbers with fractional parts you can get many more than 15 digits in the decimal representation, because of the incommensurability of decimal and binary fractions.

他将其描述为“精度的小数位”是完全错误的。如果 A都在小数点之前,则精度为double15 位十进制数字对于带有小数部分的数字,由于十进制和二进制分数的不可公度性,您可以在十进制表示中获得多于 15 位的数字。

回答by Maljam

You could also "measure" it directly:

您也可以直接“测量”它:

for(double d = 1 ; d > 0 ; d/=2) System.out.println(d);

The idea of this code is to reach the smallest number with one single bit. So you start with 1(which only has 1 bit) and divide by two (which shifts bits towards the right in binary) until you reach the last bit. The last number printed by this loop is:

这段代码的想法是用一位来达到最小的数字。因此,您从1(只有 1 位)开始并除以 2(以二进制形式向右移动位),直到到达最后一位。此循环打印的最后一个数字是:

4.9E-324

4.9E-324

回答by Sci Prog

Run this code, and see where it stops

运行这段代码,看看它在哪里停止

public class FindPrecisionDouble {
  static public void main(String[] args) {
    double x = 1.0;
    double y = 0.5;
    double epsilon = 0;
    int nb_iter = 0;
    while ((nb_iter < 1000) && (x != y)) {
        System.out.println(x-y);
        epsilon = Math.abs(x-y);
        y = ( x + y ) * 0.5;
    }
    final double prec_decimal = - Math.log(epsilon) / Math.log(10.0);
    final double prec_binary = - Math.log(epsilon) / Math.log(2.0);
    System.out.print("On this machine, for the 'double' type, ");
    System.out.print("epsilon = " );
    System.out.println( epsilon );
    System.out.print("The decimal precision is " );
    System.out.print( prec_decimal );
    System.out.println(" digits" );
    System.out.print("The binary precision is " );
    System.out.print( prec_binary );
    System.out.println(" bits" );
  }
}

Variable ybecomes the smallest value different than 1.0. On my computer (Mac Intel Core i5), it stops at 1.1102...E-16. It then prints the precision (in decimal and in binary).

变量y成为不同于 的最小值1.0。在我的电脑(Mac Intel Core i5)上,它停在1.1102...E-16. 然后打印精度(十进制和二进制)。

As stated in https://en.wikipedia.org/wiki/Machine_epsilon, floating-point precision can be estimated with the epsilon value. It is "the smallest number that, when added to one, yields a result different from one" (I did a small variation: 1-e instead of 1+e, but the logic is the same)

https://en.wikipedia.org/wiki/Machine_epsilon 所述,浮点精度可以用 epsilon 值估计。它是“最小的数,当加到 1 时,产生的结果不同于 1”(我做了一个小的变化:1-e 而不是 1+e,但逻辑是一样的)

I'll explain in decimal: if you have a 4-decimals precision, you can express 1.0000 - 0.0001, but you cannot express the number 1.00000-0.00001 (you lack the 5th decimal). In this example, with a 4-decimals precision, the epsilon is 0.0001. The epsilon directly measures the floating-point precision. Just transpose to binary.

我会用十进制解释:如果你有 4 位小数的精度,你可以表达 1.0000 - 0.0001,但你不能表达数字 1.00000-0.00001(你缺少第五位小数)。在此示例中,使用 4 位小数精度时,epsilon 为 0.0001。epsilon 直接测量浮点精度。只需转置为二进制。

EditYour question asked "How to determine...". The answer you were searching were more an explanation of than a way to determine precision (with the answer you accepted). Anyways, for other people, running this code on a machine will determine the precision for the "double" type.

编辑您的问题是“如何确定...”。您正在搜索的答案与其说是确定精度的方法,不如说是一种解释(使用您接受的答案)。无论如何,对于其他人来说,在机器上运行此代码将确定“double”类型的精度。

回答by entpnerd

The max precision of doubleof is the first value greater than 0. According Double's Javadoc, this number is represented by Double.MIN_VALUE. You can output it as follows:

of 的最大精度double是第一个大于 0 的值。根据 Double 的 Javadoc,这个数字由 表示Double.MIN_VALUE。您可以按如下方式输出:

BigDecimal doubleMinVal = BigDecimal.valueOf(Double.MIN_VALUE);
System.out.println(doubleMinVal.toPlainString());
System.out.println(doubleMinVal.toString());

See this IDEOne programfor an example.

有关示例,请参阅此 IDEOne 程序