简体   繁体   中英

What is the reason of not executing all of the threads in an unbounded threadpool executer

I am using an ExecutorService
ExecutorService executor = Executors.newFixedThreadPool(20000);
And I have in the ThreadSystem.java class two static members:

public static Integer count = 0;
public static Integer rejectedCount = 0;

then I'm adding threads to it:

for (i = 0; i < 20001; i++) {
    Runnable worker = new MyThread();
    try {
        executor.execute(worker);
    } catch (RejectedExecutionException ex) {
        rejectedCount++;
    }
}
executor.shutdown();
while (!executor.isTerminated()) {
}

Inside the thread:

@Override
public void run() {
    ThreadSystem.count++;
    try{   
        Thread.sleep(50);       
    }
    catch(InterruptedException ex){
        Logger.getLogger(MyThread.class.getName()).log(Level.SEVERE, ex.getMessage(),ex);
      }
}

The results I'm getting indicate that there are threads that are not executed and the count variable is not equal to the number of threads created, although the rejectedCount that refers to the rejected threads is 0:

count:19488
rejected count: 0

So what else can assure me that all of the threads will run, and what is the reason of that case: the count(runnable threads) is not equal to the added threads ?

Your code is the "perfect example" of a race-condition: Your access to

 public static Integer count = 0;

is not synchronized, so several threads may do this line at the same time:

 ThreadSystem.count++;

This can/may result in writes being lost, because several threads may at the same time do the equivalent of ThreadSystem.count = ThreadSystem.count + 1 , and some will read the old and not-yet updated number for the operation.

Either use appropriate synchronized guards or use something along AtomicInteger#incrementAndGet() for the counter.

Note, that you must not synchronize on the count in this case, since Integer is an immutable object and operations on boxed primitives ( int to Integer , long to Long , ...) are basically assignments to the variable. Using AtomicInteger is the best solution for this given problem.

The same is true for your rejectedCount . (Not true, since this is updated only by one thread.)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM