对于这个代码块:

int num = 5;
int denom = 7;
double d = num / denom;

d值为0.0。它可以通过施法强制工作:

double d = ((double) num) / denom;

但是有没有其他方法可以得到正确的双重结果呢?我不喜欢使用原始类型,谁知道会发生什么。


当前回答

类型转换是唯一的方法

也许你不会明确地这么做,但它会发生。

现在,有几种方法可以尝试获得精确的双精度值(其中num和denom是int类型,当然还有强制转换)

使用显式强制转换:

Double d = (Double) num / denom; Double d = ((Double) num) / denom; Double d = num / (Double) denom; Double d = (Double) num / (Double) denom;

但不是double d = (double) (num / denom);

使用隐式强制转换:

Double d = num * 1.0 / denom; Double d = num / 1d / denom; Double d = (num + 0.0) / denom; Double d = num;D /= denom;

d = num / denom * 1.0; d = 0.0 + (num / denom);


现在如果你问,哪个更好?明确吗?还是隐式?

好吧,我们不要直接回答。简单地记住——我们程序员不喜欢源代码中的惊喜或魔法。我们真的很讨厌复活节彩蛋。

另外,额外的操作肯定不会使您的代码更有效率。对吧?

其他回答

类型转换是唯一的方法

也许你不会明确地这么做,但它会发生。

现在,有几种方法可以尝试获得精确的双精度值(其中num和denom是int类型,当然还有强制转换)

使用显式强制转换:

Double d = (Double) num / denom; Double d = ((Double) num) / denom; Double d = num / (Double) denom; Double d = (Double) num / (Double) denom;

但不是double d = (double) (num / denom);

使用隐式强制转换:

Double d = num * 1.0 / denom; Double d = num / 1d / denom; Double d = (num + 0.0) / denom; Double d = num;D /= denom;

d = num / denom * 1.0; d = 0.0 + (num / denom);


现在如果你问,哪个更好?明确吗?还是隐式?

好吧,我们不要直接回答。简单地记住——我们程序员不喜欢源代码中的惊喜或魔法。我们真的很讨厌复活节彩蛋。

另外,额外的操作肯定不会使您的代码更有效率。对吧?

double num = 5;

这样就避免了转换。但是您会发现强制转换是定义良好的。你不用猜,只要看看JLS就知道了。Int到double是一个扩大转换。从§5.1.2:

扩展基元转换则不然 失去关于整体的信息 数值的大小。 […] 整型或长值的转换 浮动:浮动,或具有长值 加倍,可能导致损失 精确——也就是说,结果可能会失败 一些最不重要的片段 值。在这种情况下,结果 浮点值是a 的正确四舍五入版本 整数值,使用IEEE 754 四舍五入模式(§4.2.4)。

5可以被精确地表示为double。

最好的办法是

int i = 3;
Double d = i * 1.0;

d is 3.0 now.

铸造原语有什么问题?

如果你因为某种原因不想施法,你可以这样做

double d = num * 1.0 / denom;

可以使用以下语句:

double step = 1d / 5;

(1d是双重施法)