[Thread pool] The correct way to create a thread pool

The correct way to create a thread pool

The thread pool can be created automatically through the Executors tool class, or manually. For how to choose, the "Java Development Manual" has the following description:

Thread pools are not allowed to be created using Executors, but through ThreadPoolExecutor. This allows developers to more clearly define the operating rules of the thread pool and avoid the risk of resource exhaustion.
Disadvantages of Executros generating thread pool objects:

  • FixedThreadPool and SingleThreadPool: The allowed request queue length is Integer.MAX_VALUE, which may accumulate a large number of requests, leading to OOM.
  • The number of threads that CachedThreadPool allows to create is Integer.MAX_VALUE, which may create a large number of threads, leading to OOM.
    Insert picture description here

Examples of FixedThreadPool memory overflow

FixedThreadPool uses an unbounded queue, and the upper limit of the capacity is Integer.MAX_VALUE. When more and more requests are not processed in time, it will take up a lot of memory, resulting in OOM.

public class FixedThreadPoolOOM {
    
    
    public static void main(String[] args) {
    
    
        ExecutorService pool = Executors.newFixedThreadPool(1);
        for(int i = 0; i < Integer.MAX_VALUE; i++) {
    
    
            System.out.println(i);
            pool.execute(new Task());
        }
    }
}

class Task implements Runnable{
    
    

    @Override
    public void run() {
    
    
        try {
    
    
            TimeUnit.SECONDS.sleep(1000);
        } catch (InterruptedException e) {
    
    
            e.printStackTrace();
        }
    }
}

In order to be able to overflow the memory as soon as possible, adjust the JVM parameters as follows

-Xms8M -Xmx8M

Operation result: When the memory overflows, there are 164963 tasks in the work queue.

164963
Exception in thread "main" java.lang.OutOfMemoryError: GC overhead limit exceeded
	at java.lang.Integer.toString(Integer.java:403)
	at java.lang.String.valueOf(String.java:3099)
	at java.io.PrintStream.print(PrintStream.java:597)
	at java.io.PrintStream.println(PrintStream.java:736)
	at com.lzp.java.concurrent.threadpool.FixedThreadPoolOOM.main(FixedThreadPoolOOM.java:19)

Calculation of the number of core threads

According to different business scenarios, set the thread pool parameters yourself, such as how large the memory is, thread names, etc.

  • CPU-intensive tasks (encryption, computing hash, etc.): The optimal number of threads is 1-2 times the number of CPU cores.
  • Time-consuming IO type (read and write database, file, network read and write, etc.): The optimal number of threads is generally many times larger than the number of CPU cores, based on the busy status displayed by the JVM thread monitoring, to ensure that the threads can be connected when they are idle. The estimation formula is
线程数 = CPU核心数 * (1 + 平均等待时间 / 平均工作时间)

If more accurate values ​​are required, pressure testing is required.

Guess you like

Origin blog.csdn.net/LIZHONGPING00/article/details/105155932