什么是圆一个浮动值在Java最接近的整数的最有效方法是什么?(What is the most ef

2019-07-31 03:23发布

我已经看到了SO相关四舍五入浮点值的讨论很多,但是没有坚实的Q&A考虑到效率方面。 所以在这里,它是:

什么是圆一个浮点数值最接近的整数最有效的(但正确)的方式?

(int) (mFloat + 0.5);

要么

Math.round(mFloat);

要么

FloatMath.floor(mFloat + 0.5);

或者是其他东西?

最好我想使用标准的Java库中可用,我不得不进口的东西,而不是一些外部库。

Answer 1:

public class Main {
    public static void main(String[] args) throws InterruptedException {
        for (int i = 0; i < 10; i++) {
            measurementIteration();
        }
    }

    public static void measurementIteration() {
        long s, t1 = 0, t2 = 0;
        float mFloat = 3.3f;
        int f, n1 = 0, n2 = 0;
        for (int i = 0; i < 1E4; i++) {
            switch ((int) (Math.random() * 2)) {
            case 0:
                n1 += 1E4;
                s = System.currentTimeMillis();
                for (int k = 0; k < 1E4; k++)
                    f = (int) (mFloat + 0.5);
                t1 += System.currentTimeMillis() - s;
                break;
            case 1:
                n2 += 1E4;
                s = System.currentTimeMillis();
                for (int k = 0; k < 1E4; k++)
                    f = Math.round(mFloat);
                t2 += System.currentTimeMillis() - s;
                break;
            }
        }
        System.out.println(String.format("(int) (mFloat + 0.5): n1 = %d    -> %.3fms/1000", n1, t1 * 1000.0 / n1));
        System.out.println(String.format("Math.round(mFloat)  : n2 = %d    -> %.3fms/1000", n2, t2 * 1000.0 / n2));
    }
}

关于Java SE6输出:

(int) (mFloat + 0.5): n1 = 500410000    -> 0.003ms/1000
Math.round(mFloat)  : n2 = 499590000    -> 0.022ms/1000

关于Java SE7(感谢Alex的结果)输出:

(int) (mFloat + 0.5): n1 = 50120000 -> 0,002ms/1000
Math.round(mFloat) : n2 = 49880000 -> 0,002ms/1000

正如你所看到的,这里面有巨大的性能提升Math.round从SE6到SE7。 我认为,在SE7没有显著差异了,你应该选择什么似乎更具可读性你。



Answer 2:

基于Q&A的,我想你指的是,各种方法的相对效率取决于你所使用的平台上

但底线是:

  • 最新的JRE有业绩修正Math.floor / StrictMath.floor ,和
  • 除非你正在做一个可怕很多圆的,它可能不会让你做哪种方式有什么区别。

参考文献:

  • 这是否意味着Java的Math.floor极其缓慢?
  • http://bugs.sun.com/view_bug.do?bug_id=6908131 ( “java.lang.StrictMath.floor(双)java.lang.StrictMath.ceil的纯Java实现(双)”)


Answer 3:

我应该去Math.round(mFloat)的原因,而是encapsuling的方法舍入逻辑(即使它不是你的方法)。

其根据文档你写的代码是相同的是Math.round执行(除非它检查边界的情况下)。

反正什么是更重要的是你的算法的时间复杂度,而不是时间,小恒状的东西......除了你是编程的东西,将被调用数百万次! :d

编辑:我不知道FloatMath。 它是从JDK?



Answer 4:

您可以使用它的基准System.currentTimeMillis() 你会看到,不同的是太少



Answer 5:

简单地增加0.5将为负数不正确的结果。 见更快地实现Math.round的? 为更好的解决方案。



文章来源: What is the most efficient way to round a float value to the nearest integer in java?