0

below is my code. I am populating a list with size 3500000 by thread. first i populated the list by one thread. And This thread will return a list of string that contains 3500000 items.

This Process Takes 5 seconds to execute.

Then, I created another Thread and divided the entire task by two and distributed them to the threads.

First thread will populate the list of string of 1900000 items, second thread will return (3500000-1900000=1600000) items. The two process are running in parallel. So, the should take less time. But, for this case, the total computing time is also 5 seconds.

Please anybody help me out to find out where I am doing wrong?

I badly need to minimize the execution time. How I can minimize the time?

package callablefutures;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.Calendar;
import java.util.concurrent.TimeUnit;
import java.util.Date;

public class CallableFutures {

  private static final int NTHREDS = 10;
  public static void main(String[] args) {

  ExecutorService executor = Executors.newFixedThreadPool(NTHREDS);
  List<Future<List<String>>> list = new ArrayList<Future<List<String>>>();


    List<List<String>> lst=new ArrayList();
    List<String> list1=new ArrayList();
    List<String> list2=new ArrayList();


  Runtime rt = Runtime.getRuntime();
  long prevFree = rt.freeMemory();
  long startTime=System.currentTimeMillis();


      Callable<List<String>> worker = new MyCallable(list1,0,1900000);
      Future<List<String>> submit = executor.submit(worker);
      list.add(submit);

      Callable<List<String>> worker1 = new MyCallable(list2,1900000,3500000);
      Future<List<String>> submit1 = executor.submit(worker1);
      list.add(submit1);

    long sum = 0;
    System.out.println(list.size());

    for (Future<List<String>> future : list) {
      try {
          lst.add(future.get());
      } catch (InterruptedException e) {
        e.printStackTrace();
      } catch (ExecutionException e) {
        e.printStackTrace();
      }
    }
    executor.shutdown();
  long endTime=System.currentTimeMillis();
    System.out.println("Total Time Taken: " + (endTime-startTime)/1000%60 +" Seconds");
    System.out.println("Total Memory Taken (MB): " + ((prevFree-rt.freeMemory())/1024)/1024);
  }
}



package callablefutures;
import java.util.concurrent.Callable;
import java.util.List;
import java.util.ArrayList;

public class MyCallable implements Callable<List<String>>{
  public List<String> StrList=new ArrayList();
  public int sIndex,eIndex;
  public MyCallable(List<String> oList,int si,int ei)
  {
      this.StrList=oList;
      this.sIndex=si;
      this.eIndex=ei;
  }
  @Override
  public List<String> call() throws Exception {

    for (int i = this.sIndex; i < this.eIndex; i++) {
      this.StrList.add("ID  "+i);
    }
    return this.StrList;
    //return this.StrList;
  }

}
Cœur
  • 37,241
  • 25
  • 195
  • 267
dpkkry
  • 1
  • 3
  • 1
    Your Benchmark is mostly just allocating memory - quite likely it won't scale that well. You might try `new ArrayList(1900000)` to preallocate at least the lists, but I doubt that will help much. Benchmarking code running in a modern JVM is not easy, and you're doing it wrong: http://stackoverflow.com/questions/504103/how-do-i-write-a-correct-micro-benchmark-in-java – Chris Jul 01 '14 at 05:59

1 Answers1

0

You are creating about 128 MB of data, which will be larger than your L3 cache so you will be pushing data out to main memory and this is typically easy to saturate with one thread. If you want threads to run concurrently you want them to be limited to 256 KB each (as they each have their own L2 cache assuming they run on different cores) or 128 KB each if on the same core.

Peter Lawrey
  • 525,659
  • 79
  • 751
  • 1,130
  • Can you please provide me an example java code so that I can really see that applying multi threading, execution time can be reduced...theoretically I know it is possible but practically I am not being able to produce it. Please help me out!, Thanks. – dpkkry Jul 01 '14 at 08:55
  • Change your program to do something CPU intensive, not memory or IO inenstive e.g. calculate Fibonacci numbers by recursion. (Obviously iteration is much faster but as an example) – Peter Lawrey Jul 01 '14 at 11:16