Java loop gets slower after some runs / JIT's fault?

前端 未结 3 586
执笔经年
执笔经年 2020-12-05 15:44

So I wanted to benchmark some basic java functionality to add some imformation to this question: What is the gain from declaring a method as static.

I know writing b

3条回答
  •  独厮守ぢ
    2020-12-05 16:35

    It looks like is the way Java is adding values to variable r. I've made a few changes, adding method run2():

    public class TestPerformanceOfStaticVsDynamicCalls {
        private static final long RUNS = 1_000_000_000L;
        public static void main(String[] args) {
            System.out.println("Test run 1 =================================");
            new TestPerformanceOfStaticVsDynamicCalls().run();
            System.out.println("Test run 2 =================================");
            new TestPerformanceOfStaticVsDynamicCalls().run2();
        }
        private void run2() {
            long r = 0;
            long start, end;
            for (int loop = 0; loop < 10; loop++) {
                // Benchmark
                long stat = 0;
                start = System.currentTimeMillis();
                for (long i = 0; i < RUNS; i++) {
                    stat += addStatic(1, i);
                }
                end = System.currentTimeMillis();
                System.out.println("Static: " + (end - start) + " ms");
                long dyna = 0;
                start = System.currentTimeMillis();
                for (long i = 0; i < RUNS; i++) {
                    dyna += addDynamic(1, i);
                }
                end = System.currentTimeMillis();
                System.out.println("Dynamic: " + (end - start) + " ms");
                // If you really want to have values in "r" then...
                r += stat + dyna;
                // Do something with r to keep compiler happy
                System.out.println(r);
            }
        }
        private void run() {
            long r = 0;
            long start, end;
            for (int loop = 0; loop < 10; loop++) {
                // Benchmark
                start = System.currentTimeMillis();
                for (long i = 0; i < RUNS; i++) {
                    r += addStatic(1, i);
                }
                end = System.currentTimeMillis();
                System.out.println("Static: " + (end - start) + " ms");
                start = System.currentTimeMillis();
                for (long i = 0; i < RUNS; i++) {
                    r += addDynamic(1, i);
                }
                end = System.currentTimeMillis();
                System.out.println("Dynamic: " + (end - start) + " ms");
                // If you really want to have values in "r" then...
                // Do something with r to keep compiler happy
                System.out.println(r);
            }
        }
        private long addDynamic(long a, long b) {
            return a + b;
        }
        private static long addStatic(long a, long b) {
            return a + b;
        }
    }
    

    The results for are:

    Test run 1 =================================
    Static: 582 ms
    Dynamic: 579 ms
    1000000001000000000
    Static: 2065 ms
    Dynamic: 2352 ms
    2000000002000000000
    Static: 2084 ms
    Dynamic: 2345 ms
    3000000003000000000
    Static: 2095 ms
    Dynamic: 2347 ms
    4000000004000000000
    Static: 2102 ms
    Dynamic: 2338 ms
    5000000005000000000
    Static: 2073 ms
    Dynamic: 2345 ms
    6000000006000000000
    Static: 2074 ms
    Dynamic: 2341 ms
    7000000007000000000
    Static: 2102 ms
    Dynamic: 2355 ms
    8000000008000000000
    Static: 2062 ms
    Dynamic: 2354 ms
    9000000009000000000
    Static: 2057 ms
    Dynamic: 2350 ms
    -8446744063709551616
    Test run 2 =================================
    Static: 584 ms
    Dynamic: 582 ms
    1000000001000000000
    Static: 587 ms
    Dynamic: 577 ms
    2000000002000000000
    Static: 577 ms
    Dynamic: 579 ms
    3000000003000000000
    Static: 577 ms
    Dynamic: 577 ms
    4000000004000000000
    Static: 578 ms
    Dynamic: 579 ms
    5000000005000000000
    Static: 578 ms
    Dynamic: 580 ms
    6000000006000000000
    Static: 577 ms
    Dynamic: 579 ms
    7000000007000000000
    Static: 578 ms
    Dynamic: 577 ms
    8000000008000000000
    Static: 580 ms
    Dynamic: 578 ms
    9000000009000000000
    Static: 576 ms
    Dynamic: 579 ms
    -8446744063709551616
    

    As for why adding directly to r, I have no clue. Maybe somebody can provide more insights on why accessing r inside the loop block makes things much slower.

提交回复
热议问题