我正在嘲笑Java中random()
类的静态Math
方法,以更好地测试依赖于生成随机数的方法。我使用的代码如下:
@Mock
public double random() {
return 1.0 - Double.MIN_VALUE;
}
这是我尝试在不相等的情况下尽可能接近1.0的值。 (例如0.999999999999 ......)
但是,当我调用模拟的Math.random()
方法时,我总是得到1.0作为值。它几乎就像减去Double.MIN_VALUE
一样,根本不会影响1.0。
为什么1.0 - Double.MIN_VALUE
会产生1.0,我如何模拟Math.random()
的最大可能值?
答案 0 :(得分:2)
double
具有限制精度。可以表示为double的最接近1.0 - Double.MIN_VALUE
的数字是1.0。这就是你得到1.0
的原因。
双精度符号为1位,指数为11位,分数为52位。 (Source)
由64位表示的double值为(-1)^sign+1.b51b50...b0 x 2^(e-1023)
最接近1.0的是当所有分数位为1且指数为e-1023==-1
时。
该值为二进制0.1111..111
(53个)。
以小数形式获取该值:
double d = 0.0;
double exp =1.0;
for (int i=1;i<=53;i++) {
exp=exp*2.0;
d+=1.0/exp;
}
System.out.println (d);
System.out.println ("d==1.0? " + (d==1.0));
打印
0.9999999999999999
d==1.0? false
如果你在循环中添加另一个迭代(即i<=54)
,你得到:
1.0
d==1.0? true
答案 1 :(得分:1)
根据IEEE 754 double有15.95个十进制数字
http://en.wikipedia.org/wiki/IEEE_floating_point
因此,如果您尝试double a = 1e0 - 1e-16 //or less
,您将获得== 1e0
答案 2 :(得分:1)
double
不够精确,无法显示执行1.0 - Double.MIN_VALUE
时生成的数字。在讨论Java原始类型时,指出了here。您可能会发现此答案也很有趣:https://stackoverflow.com/a/15736977/4381697