threads

Thread performance on Atomic type

With this example we are going to demonstrate how to check a thread performance on atomic type. We are testing two runnable objects, one that uses an AtomicInteger and another one that uses a synchronized method. The example is described in short:

  • We have created a class, AtomicRunnable that implements the Runnable, uses an AtomicInteger and in its overriden run() method increases it, using the increamentAndGet() API method of AtomicInteger.
  • We have also created a class, SyncRunnable that implements the Runnable and in its overrided run() method uses its method incrVar() in a synchronized keyword in order to increase the value of an int variable.
  • We have a static method, performanceTest(Runnable runnable) that creates new threads with the given runnables and calls their start() method to begin their execution and their join() method that waits for the threads to die.
  • We have also created a class, Timestamp, that in its start() and stop() methods gets the System.nanoTime() and in its elapsedTime() method converts the subtraction between start and end time and uses convert(long sourceDuration, TimeUnit sourceUnit) method of TimeUnit to convert time duration to the given TimeUnit.
  • We call the performanceTest(Runnable runnable) method for the two Runnables created above and we use the Timestamp class to count the time both runnables need to execute.

Let’s take a look at the code snippet that follows:

package com.javacodegeeks.snippets.core;

import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicInteger;


public class Performance {

    static int loops;
    static int threads;

    public static void main(String[] args) {


  loops = 1000;

  threads = 10;

  

  performanceTest(new AtomicRunnable());

  performanceTest(new SyncRunnable());

 

  System.out.println("Atomic test");

  cleanAll();

  Timestamp timeStamp = new Timestamp();

  performanceTest(new AtomicRunnable());

  timeStamp.stop();

  System.out.println("Atomic took " + timeStamp);


  System.out.println("Sync test");

  cleanAll();

  

  Timestamp timeStampSync = new Timestamp();

  performanceTest(new SyncRunnable());

  timeStampSync.stop();

  

  System.out.println("Sync took " + timeStampSync);


  double gained = ((double) (timeStampSync.elapsedTime() - timeStamp.elapsedTime()))


    / (loops * threads);

  System.out.println("Atomic (unsynch) operation saves " + gained + " " + timeStampSync.units()


    + " per call");
    }

    static void cleanAll() {

  System.gc();

  System.runFinalization();

  System.gc();
    }

    static class AtomicRunnable implements Runnable {


  AtomicInteger atomicInt = new AtomicInteger(1);


  @Override

  public void run() {


for (int i = 0; i < loops; i++) {


    atomicInt.incrementAndGet();


}

  }
    }

    static class SyncRunnable implements Runnable {


  int i;


  synchronized void incrVar() {


i++;

  }


  @Override

  public void run() {


for (int i = 0; i < loops; i++) {


    incrVar();


}

  }
    }

    static void performanceTest(Runnable runnable) {

  

  Thread threads[] = new Thread[Performance.threads];

  

  for (int i = 0; i < Performance.threads; i++) {


threads[i] = new Thread(runnable);

  }

  

  for (int i = 0; i < Performance.threads; i++) {


threads[i].start();

  }

  

  for (int i = 0; i < Performance.threads; i++) {


try {


    threads[i].join();


} catch (InterruptedException ie) {


}

  }
    }
}
class Timestamp {

    private long start;
    private long end;
    private boolean stopped = false;
    private TimeUnit unit;

    public Timestamp() {

  this(TimeUnit.NANOSECONDS);
    }

    public Timestamp(TimeUnit unit) {

  this.unit = unit;

  start();
    }

    public void start() {

  start = System.nanoTime();

  stopped = false;
    }

    public void stop() {

  end = System.nanoTime();

  stopped = true;
    }

    public long elapsedTime() {

  if (!stopped) {


throw new IllegalStateException("Timestamp didn't stop");

  }

  return unit.convert(end - start, TimeUnit.NANOSECONDS);
    }

    @Override
    public String toString() {

  try {


return elapsedTime() + " " + unit;

  } catch (IllegalStateException ise) {


return "Timestamp didn't stop";

  }
    }

    public String units() {

  return unit.toString();
    }
}

Output:

Atomic test
Atomic took 1110387 NANOSECONDS
Sync test
Sync took 1965840 NANOSECONDS
Atomic (unsynch) operation saves 85.5453 NANOSECONDS per call

 
This was an example of how to check a thread performance on atomic type in Java.

Byron Kiourtzoglou

Byron is a master software engineer working in the IT and Telecom domains. He is an applications developer in a wide variety of applications/services. He is currently acting as the team leader and technical architect for a proprietary service creation and integration platform for both the IT and Telecom industries in addition to a in-house big data real-time analytics solution. He is always fascinated by SOA, middleware services and mobile development. Byron is co-founder and Executive Editor at Java Code Geeks.
Subscribe
Notify of
guest

This site uses Akismet to reduce spam. Learn how your comment data is processed.

0 Comments
Inline Feedbacks
View all comments
Back to top button