Java 中 double 到 int 的转换是如何进行的?
对于以下代码(Java):
double d = (double) m / n; //m and n are integers, n>0
int i = (int) (d * n);
i == m
最后一个表达式总是为真吗? 如果不是,这总是正确的吗?:
i = (int) Math.round(d * n);
i == m
For the following code (Java):
double d = (double) m / n; //m and n are integers, n>0
int i = (int) (d * n);
i == m
Is the last expression always true?
If it's not is this always true?:
i = (int) Math.round(d * n);
i == m
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
对于 m=1、n=49,这是错误的。
我的直觉告诉我这应该是真的,但可能很难严格证明。
This is false for m=1, n=49.
My intuition tells me it should be true, but it may be hard to prove rigorously.
您问的第二个问题涉及 ulp 是 Java 语言。
如果 ulp 超过
1/(n)
,则对乘法进行舍入将无法恢复原始除法 int。通常,较大的 ulp 与较大的双精度值相关。与双精度相关的 ulp 在 9E15 左右开始超过 1;如果你恢复的双打在那里,那么你可能会发现 round() 没有得到预期答案的问题。不过,当您使用 int 值时,除法分子的最大值将为Integer.MAX_VALUE
。以下程序测试
n
的所有正整数值,以查看在尝试恢复除后的 int 时哪一个最有可能导致舍入错误:输出为:
使用 Math.round 进行舍入,然后转换为 int 应该恢复原始 int。
The second question you ask concerns how large an ulp is in Java.
If the ulp exceeds
1/(n)
, then rounding the multiplication would not recover the original divided int. Typically, larger ulps are associated with larger double values. An ulp associated with a double starts to exceed 1 at around 9E15; if your recovered doubles were around there, then you might finding problems with round() not getting the expected answer. As you are working with int values, though, the largest value of the numerator of your division will beInteger.MAX_VALUE
.The following program tests all the positive integer values of
n
to see which one causes the largest potential for rounding error when trying to recover the divided int:The output is:
Rounding that using Math.round, then casting to int should recover the original int.
从数学上来说它应该是正确的。但是,您可能会遇到浮点舍入错误,从而导致错误。您几乎不应该使用
==
来比较浮点精度数。您最好使用这样的阈值来比较它们:
请注意,这两个语句应该是等效的
但是例如,如果
d=3/2
和n=2
,浮点错误可能会导致i=2.999999999999
,截断/舍入后为 2。Mathematically it should be true. However you're likely going to get floating point rounding errors that will make it false. You should almost never compare floating point precision numbers using
==
.You're much better off comparing them using a threshold like this:
Note that the two statements should be equivalent
However for example, if
d=3/2
andn=2
, floating point errors might result ini=2.999999999999
which after truncation/rounding is 2.第一个绝对不总是正确的。第二个我会说是的,这是真的,但只是因为我想不出反例。
如果 n 很大,它可能是假的,我不确定。但我知道至少 99% 的情况下这是真的。
The first on is definitely not always true. The second one I would say yes it's true, but only because I can't think of a counterexample.
If n is very large, it could possibly be false, I'm not sure really. I know it will be true at least 99% of the time though.