title: Why execution time of this multi-threading program is so weird?
body: <pre><code>import java.util.ArrayList;
  
  
  interface ICounter {
      void inc();
      void dec();
      int get();
  }
  
  
  class Counter implements ICounter {
      protected int counter = 0;
  
      public void inc() { counter++; }
      public void dec() { counter--; }
  
      public int get() { return counter; }
  }
  
  class SynchronizedCounter extends Counter {
      public synchronized void inc() { counter++; }
      public synchronized void dec() { counter--; }
  }
  
  class BetterCounter implements ICounter {
      protected long up = 0;
      protected long down = 0;
  
      public void inc()  { up++; }
      public void dec()  { down--; }
  
      public int get() { return (int)(up + down); }
  }
  
  
  class SynchronizedBetterCounter extends BetterCounter {
      private Object lock1 = new Object();
      private Object lock2 = new Object();
  
      public void inc() { synchronized(lock1) { up++; } }
      public void dec() { synchronized(lock2) { down--; }  }
  
  }
  
  
  class Inc extends Thread {
      ICounter i;
  
      public Inc(ICounter i) { this.i = i; }
  
      public void run() {
          for(int x = 0; x &lt; 2147483647 ; x++) {
              i.inc();
          }
      }
  }
  
  class Dec extends Thread {
      ICounter i;
  
      public Dec(ICounter i) { this.i = i; }
  
      public void run() {
          for(int x = 0; x &lt; 2147483647 ; x++) {
              i.dec();
          }
      }
  }
  
  
  public class Main {
  
      public static void main(String[] args) {
          ICounter[] c = {new Counter(), new SynchronizedCounter(), new BetterCounter(), new SynchronizedBetterCounter()};
          int numberOfCounters = 4;
  
          ArrayList&lt;Inc&gt; inc = new ArrayList&lt;&gt;();
          ArrayList&lt;Dec&gt; dec = new ArrayList&lt;&gt;();
  
          for(int i = 0; i &lt; numberOfCounters; i++) {
              inc.add(new Inc(c[i]));
              dec.add(new Dec(c[i]));
          }
  
          long start = 0;
          long stop = 0;
  
          int returnVal[] = new int[4];
          long execTime[] = new long[4];
  
          for(int i = 0; i &lt; numberOfCounters; i++) {
              start = System.currentTimeMillis();
  
              inc.get(i).start();
              dec.get(i).start();
  
              try {
                  inc.get(i).join();
                  dec.get(i).join();
              } catch (InterruptedException ex) {
              }
  
              stop = System.currentTimeMillis();
              returnVal[i] = c[i].get();
              execTime[i] = stop-start;
          }
  
          for(int i = 0; i &lt; 4; i++) {
              System.out.println("Counter: " + c[i].getClass().getSimpleName());
              System.out.println("Value of counter: " + returnVal[i]);
              System.out.println("Execution time: " + execTime[i] + " ms\n");
          }
      }
  }
  </code></pre>
  
  <p>The goal is to make counter with methods <code>inc</code> to increase value and <code>dec</code> to decrease it. It's written in 4 ways - the basic, with synchronization, with 2 variables (1 to increase, 2 to decrease) and with 2 variables and synchronization. There are 2 classes <code>Inc</code> and <code>Dec</code> for multithreading.</p>
  
  <p>I know there can be problems with this code, but the goal is just to add and subtract big number, just once, as fast as possible.</p>
  
  <p><strong>Output</strong></p>
  
  <pre><code>Counter: Counter
  Value of counter: 2061724420
  Execution time: 141 ms
  
  Counter: SynchronizedCounter
  Value of counter: 0
  Execution time: 174210 ms
  
  Counter: BetterCounter
  Value of counter: 0
  Execution time: 39468 ms
  
  Counter: SynchronizedBetterCounter
  Value of counter: 0
  Execution time: 52176 ms
  </code></pre>
  
  <p><strong>Question:</strong>
  Why first execution time is so small, comparing to the others?</p>