This is the 11th day of my participation in Gwen Challenge

Author: Flower Gie

Wechat official account: Java development zero to one

preface

We have updated seven chapters of the multithreading series, and we strongly recommend that you learn them in order:

Squat can also enter the factory “multithreading series article directory

In the first few chapters, we have learned how to use threads and how to use them. However, if you are serious, you will think about whether threads can be created indefinitely. Then we can handle concurrency easily, and suddenly we feel that it is not a problem to support the concurrency of Taobao Double 11.

This is not the case. If there are a large number of concurrent threads, and each thread completes a short task, creating threads frequently reduces the efficiency of the system because it takes time to create and destroy threads frequently. In this chapter, we will show you how to solve this problem, namely the use of thread pools.

The body of the

Me: Dog, have you ever used thread pools? I see everyone is using this, isn’t it nice to create threads directly?

Let me give you an example. We have all had dinner in a hot pot restaurant. If a hot pot restaurant has 10 fixed tables, when there are 10 tables and less than 10 tables of guests to consume, the hot pot restaurant can serve at the same time, and if the number of guests is more than 10 tables, we will move a stool, open the king, and enter the long waiting. It is not until the other guests have had enough to eat and drink that the next guest enters in order.

However, when it comes to Friday night (I don’t know when everyone is), our company partners like to have dinner on Friday night very much anyway. At this time, there are a lot of people at this time, and the line may be dozens of meters long. At this time, the smart boss thinks, so many customers and so long wait, the customer experience is too poor. So the owner quickly rented 5 tables from an unknown hot pot restaurant next door and put them into the store. In this way, there are 15 tables in the store, greatly reducing the waiting time for customers.

However, it is possible that even if five tables are rented, the waiting line is still very long, and the boss can only tell the subsequent guests that today is full, sorry. By the end of the week, everyone was paddling again, and since no one was eating, the boss returned the borrowed table.

Let’s look at a flow chart to illustrate the process:

Me: dog son, you are to make up the word count, say so much?

You this is the dog bites Lv Dongbin, say so much is not still for you and small partner people good understanding.

Me: Ok ok, I am wrong about you, give you a thumbs up. So what are the specific benefits of using a thread pool, I’m just interested in how to answer an interview? Do not share this example with your interviewer….

Silly dog… This example is just for understanding. The advantages of thread pools are summarized as follows:

  • Reduce resource consumption. Creating threads repeatedly is expensive, and thread pools reduce consumption by reusing threads that have been created.
  • Improve response speed. The thread pool maintains a portion of the core threads that execute tasks without being destroyed and can execute the next task when it comes in without having to create it.
  • Improved thread control. Thread pooling enables uniform thread allocation, tuning, and monitoring.

Me: So how do I use thread pools?

The thread pool at the core of a class is the Java uitl. Concurrent. ThreadPoolExecutor, its construction method has four kinds:

public class ThreadPoolExecutor extends AbstractExecutorService {...public ThreadPoolExecutor(int corePoolSize,int maximumPoolSize,long keepAliveTime,TimeUnit unit,
            BlockingQueue<Runnable> workQueue);
 
    public ThreadPoolExecutor(int corePoolSize,int maximumPoolSize,long keepAliveTime,TimeUnit unit,
            BlockingQueue<Runnable> workQueue,ThreadFactory threadFactory);
 
    public ThreadPoolExecutor(int corePoolSize,int maximumPoolSize,long keepAliveTime,TimeUnit unit,
            BlockingQueue<Runnable> workQueue,RejectedExecutionHandler handler);
 
    public ThreadPoolExecutor(int corePoolSize,int maximumPoolSize,long keepAliveTime,TimeUnit unit,
        BlockingQueue<Runnable> workQueue,ThreadFactory threadFactory,RejectedExecutionHandler handler); . }Copy the code

Based on the above four creation methods, the following parameters can be sorted out:

  • CorePoolSize:The size of the core thread count. By default, after the thread pool is created, the number of threads in the thread pool is 0. When a task comes in, a thread is created to execute the taskcorePoolSizeAfter that, the incoming task is placed in the cache queue.
  • MaximumPoolSize:The maximum number of threads allowed to be created in the thread pool whenActive threadsAfter this value is reached, subsequent new tasks will block;
  • KeepAliveTime:Idle timeout duration of a thread. By default, when the number of threads is greater thanCore threads, keepAliveTime will take effect, that is, a thread idle time reaches keepAliveTime, will be reclaimed until the number of threads does not exceedCore threads. But if you call itallowCoreThreadTimeOut(boolean)Method, the number of core threads is also reclaimed until the number of threads in the thread pool reaches zero;
  • Unit: Specifies the unit of keepAliveTime. The common value is timeunit. SECONDS.
  • WorkQueue: a blocking queue that stores tasks to be executed. Details about common queues are described below.
  • ThreadFactory: threadFactory. Used to specify how new threads are created for the thread pool;
  • Handler: rejects the policy. The saturation strategy that needs to be executed when the maximum number of threads is reached.

Me: This one introduced my scalp pins and needles, completely confused.

Don’t worry, big boobs. Here’s the flow chart. A picture is worth a thousand words:

From the above figure, combined with the interpretation of each parameter, you have a general understanding of all parameters. The number of core threads, the maximum number of threads, and the timeout period are easy to understand, but the task queue and rejection policy are explained in more detail below.

Me: Let’s talk about the queues we use.

As you can see from the flow chart, when the number of core threads is exhausted, tasks that can’t be processed are put into a blocking queue waiting to be executed. There are three most commonly used queues, as follows:

  • ArrayBlockingQueue: A bounded blocking queue consisting of an array structure that implements a circular queue with Pointers.

  • SynchronousQueue: a blocking queue that does not store elements, which blocks when a consumer thread calls take() until a producer thread produces an element, which the consumer thread can retrieve and return; The producer thread also blocks when it calls the put() method and does not return until one of the consumer threads consumes an element.

  • LinkedBlockingDeque: a bounded two-ended blocking queue implemented using a two-way queue. Double-endian means you can FIFO (first in, first out) like a normal queue, or you can FILO (first in, last out) like a stack.

Me: I see. What’s a rejection strategy?

When the number of new threads in the thread pool reaches the maximum number of threads, the closers execute the rejection policy. Executors provide four rejection strategies:

  • AbortPolicy: indicates the default rejection policy. Discarding the task and throw RejectedExecutionException anomalies.
  • DiscardPolicy: Discards the task without throwing an exception.
  • DiscardOldestPolicy: Discards the task at the top of the queue and tries to execute the task again
  • CallerRunsPolicy: This task is handled by the calling thread

Me: Oh my God, creating a thread pool is so much to think about, stop playing.

Hold on, if we’re not too demanding and we don’t like the thread pool method, right? 4 common function thread pools can be used directly by Executors, as follows:

  • NewFixedThreadPool: The maximum number of threads is equal to the number of core threads. The queue used is LinkedBlockingQueue, which has no capacity to go online. Therefore, if the number of threads is increasing and the number of requests cannot be processed in a timely manner, no new threads will be added to the queue.

Usage scenario: Control the number of concurrent threads by limiting the maximum number of threads.

The demo code:

ExecutorService service = Executors.newFixedThreadPool(10);
for (int i = 0; i < 1000; i++) {
    service.execute(new Runnable() {
        @Override
        public void run(a) {
            System.out.println("Thread name:"+ Thread.currentThread().getName()); }}); }Copy the code
  • NewSingleThreadExecutor: Basically the same principle as newFixedThreadPool, except that the number of threads is set directly to 1, thus causing the same problem.

Application scenario: Not applicable to concurrent scenarios.

The demo code:

ExecutorService service = Executors.newSingleThreadExecutor();
for (int i = 0; i < 1000; i++) {
    service.execute(new Runnable() {
        @Override
        public void run(a) {
            System.out.println("Thread name:"+ Thread.currentThread().getName()); }}); }Copy the code
  • CachedThreadPool: It can create threads indefinitely, use SynchronousQueue as a queue (no storage elements), and automatically reclaim redundant threads. The disadvantages are that maximumPoolSize is set to integer.max_value, which can result in creating too many threads. OOM.

Application scenario: Suitable for processing a large number of concurrent requests, and each request takes a short time.

The demo code:

ExecutorService service = Executors.newCachedThreadPool();
for (int i = 0; i < 1000; i++) {
    service.execute(new Runnable() {
        @Override
        public void run(a) {
            System.out.println("Thread name:"+ Thread.currentThread().getName()); }}); }Copy the code
  • NewScheduledThreadPool: thread pool that supports scheduled and periodic task execution.

Application scenario: Perform scheduled or periodic tasks.

The demo code:

public class ThreadPoolDemo {
 public static void main(String[] args) {
    // Usage 1: execute after 3 seconds
    ScheduledExecutorService service = Executors.newScheduledThreadPool(10);
    service.schedule(new ThreadTask(),3,TimeUnit.SECONDS);

    // Usage 2: Execute after 3 seconds for the first time, and execute every 5 seconds after the first time
    service.scheduleAtFixedRate(new ThreadTask(),3.5,TimeUnit.SECONDS); }}class ThreadTask implements Runnable{
 @Override
 public void run(a) {
     System.out.println("Hi, I'm Flowergie."); }}Copy the code

I: feel strange knowledge has increased, so multithreaded pool, how should I choose?

We need to choose the thread pool that fits our business scenario, for example, we want to customize the thread name, log when the task is rejected, and take into account our own memory size.

If you want to in-depth understanding of the thread pool, the source code is still very necessary to see, I now and you say….

Me: Stop…. I’m about to burst right now, but I’ll deal with it tomorrow

conclusion

Above is the basic usage of thread pool, and common parameter introduction, which involves a part of the queue knowledge, will be introduced in detail later. In the next chapter, we will parse the source code of the thread pool, but also understand why, so that we can fully grasp its essence.

Pay attention to avoid getting lost

The above is the whole content of this issue, if there is any mistake, please leave a message for advice, thank you very much. I’m GieGie, feel free to leave a comment and we’ll see you next time at 🦮.

The article continues to update, you can wechat search Java development zero to one for the first time to read, and you can get interview materials learning video, interested partners welcome to pay attention to, learn together, ha 🐮🥃.

Original is not easy, how can you bear to whoring for nothing, if you think this article is a little useful to you, thank old tie for this article to like, comment or forward, because this will be my output more quality articles of power, thank you!

Refer to blog post:

www.cnblogs.com/dolphin0520…

www.cnblogs.com/superfj/p/7…

Blog.csdn.net/u013541140/…

www.cnblogs.com/trust-freed…