【问题标题】:What happens when converting double (or floats) to ints?将双精度(或浮点数)转换为整数时会发生什么?
【发布时间】:2011-11-02 19:35:45
【问题描述】:

我正在练习一些简单的 2D 游戏编程,并提出了一个理论,即在动画期间(图像位置的实际变化最好用浮点数计算)。我有一种感觉,如果您使用整数移动图像,动画将不会那么流畅。

在 Java 中,您似乎无法使用浮点数绘制图像来为图像指定位置。但显然,当您最初声明您的 xy 时,您可以将它们声明为 Double 或 Float,而在实际绘制图像时,您必须投射他们到整数。就像我找到HERE

    /**
 * Draw this entity to the graphics context provided
 * 
 * @param g The graphics context on which to draw
 */
public void draw(Graphics g) {
    sprite.draw(g,(int) x,(int) y);
}

我的问题是 Java 如何处理转换? 如果代码在最后一分钟投出这些双打,为什么一开始就把它们当作双打呢? Java 会隐藏小数点后的数字吗?

我知道在 C 和 C++ 中,小数点后的数字会被截掉,而你只能看到它之前的数字。 Java 如何处理这种转换?

【问题讨论】:

  • 它只是去掉小数点,与 C、C++ 相同。 fluffycat.com/Java/Casting
  • 你应该尽可能多地做 double 计算,当你最终将它传递给一个接受 int 的方法时,你做 Math.round()。

标签: java casting 2d


【解决方案1】:

显示器上的像素是离散的且数量有限;因此显示坐标必须是整数 - 浮点数没有意义,因为您实际上没有像素,例如(341.4, 234,7).

也就是说,整数只能在最终绘制阶段使用。当您计算物体运动、速度等时,您需要使用浮点数。整数会导致数量惊人的精度问题。考虑以下 sn-p:

a = 1;
x = (a / 2) * 2;

如果ax 是浮点数,则x 最终将具有预期的1 数。如果它们是整数,你会得到0

基线:使用浮点类型进行物理计算并在绘图时转换为int。这将允许您以尽可能高的精度执行物理计算。

编辑:

就从 FP 数到整数的转换而言,虽然 FP 数具有更大的范围,但在归一化为绘图区域大小后由物理计算产生的值通常不会溢出 int 类型。

也就是说,Java 在转换为整数类型时会截断浮点数,这可能会产生伪像(例如,最右边像素列没有像素的动画,因为例如 639.9 被转换为 639 而不是640)。您可能想查看Math.round() 或 Java 提供的其他一些舍入方法以获得更合理的结果。

【讨论】:

    【解决方案2】:

    Java 会截断小数。例如:

    (int) 2.34 == 2
    (int) 2.90 == 2
    

    无法在浮动位置绘制的原因仅仅是没有半像素等:)

    【讨论】:

    • 我明白了。感谢您的输入,这是有道理的
    【解决方案3】:

    Java 通过删除小数将浮点数转换为 int。但我认为在浮点数中使用 x 和 y 坐标没有任何意义。屏幕上有像素,不能以小于一个像素的形式呈现。例如,您不能绘制像素.5px x .5px,因为在屏幕上它只是1px x 1px 像素。我不是计算机游戏程序员,但我用 Java 编写了一个动画引擎,它非常流畅。如果你愿意,我可以分享这个。

    请注意,您应该使用整数进行绘制,但使用双精度数进行所有计算。对于像旋转或任何依赖数学公式的事情,应该以十进制完成。

    【讨论】:

    • 浮点数之所以有用有多种原因——其中,sin/cos(几乎是体面旋转的必要条件)实际上需要它们,许多矩阵运算可以从数字能力中受益取小数值。你把它们变成整数,你最终会失去很多灵活性(除非你想编写自己的整数三角函数等)。很多人会将它们保留为双精度或浮点数,直到它们绝对必须是整数。
    • 这是真的。我并不是要以整数进行计算。在我的应用程序中,我仍然使用双精度进行所有计算并使用整数进行绘制。我将更新以反映此说明。
    • @AmirRaminfar 我可以看一下吗?
    • 你当然可以。 github.com/amir20/iAuthor/tree/master/animation/src/main/java/… 我用一个简单的动画队列实现了我自己的缓动,该队列负责处理线程。它工作得很好,而且代码行数不是很大。
    【解决方案4】:

    x 和 y 需要为双精度的原因是因为它们需要进行数学计算,例如:

    x += (delta * dx) / 1000;
    

    在绘制像素之前,您希望避免溢出和精度损失。

    【讨论】:

    • 所以我猜在 double 被铸造之前,它被计算为尽可能接近最近的准确 int? (如果这有意义的话O_o)
    猜你喜欢
    • 2014-01-30
    • 2015-06-12
    • 1970-01-01
    • 2018-04-26
    • 1970-01-01
    • 1970-01-01
    • 2018-08-09
    • 2011-11-22
    • 1970-01-01
    相关资源
    最近更新 更多