如何确定double的最大精度

我试图确定双精度的最大精度是多少。 在此链接中对已接受答案的注释中, 在Java中保留精度为double @PeterLawrey表示最大精度为15。

你怎么决定这个?

@PeterLawrey表示最高精度为15。

这实际上不是他所说的。 他说的是:

double有15位小数的精度

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

任何数字中的小数位数由其日志给予基数10. 15是log 10 (2 53 -1)的最低值,其中53是尾数的位数(包括隐含位),如因此,在Javadoc和IEEE 754中描述的和2 53 -1是最大可能的尾数值。 实际值是15.954589770191003298111788092734到Windows计算器的限制。

将它描述为’精确度的小数位’是完全错误的。 如果double 都在小数点之前,则 double的精度为15位十进制 对于具有小数部分的数字,由于十进制和二进制分数的不可通约性,您可以在十进制表示中获得多于15位的数字。

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

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

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

4.9E-324

运行此代码,并查看它停止的位置

 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(xy); epsilon = Math.abs(xy); 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" ); } } 

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

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

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

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

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

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

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