Java之“线程池”

1、为何要引入线程池

传统的多线程任务的执行策略是“即时创建,即时销毁”。这种策略存在明显的弊端:当需要线程的执行任务时间较短,而执行次数比较频繁的时候,系统就处于不停的创建线程,销毁线程的状态。

2、线程池有什么优点

而线程池能够有效减少创建的线程个数。通常线程池所允许的并发线程是有上限的,如果同时需要并发的线程数超过上限,那么一部分线程将会等待。

线程池的出现正是着眼于减少线程本身带来的开销(线程创建和销毁所带来的时间消耗)。

3、线程池常用的用法

思路:

线程池采用预创建的技术,在应用程序启动之后,立即创建一定数目的线程,放入空闲队列中。

这些线程都处于阻塞(挂起)状态,不消耗CPU资源,只占用较小的内存空间。

当任务到来后,缓冲池选择一个空闲线程,把任务传入此线程中运行。

当线程池中的线程都在处理任务时,线程池自动创建一定数量的新线程,用于处理更多的任务。

在任务执行完毕后线程不退出,而是继续保持在线程中(阻塞或挂起)等待下一次的任务。

当系统比较空闲时,大部分线程处于暂停状态,线程池自动销毁一部分线程,回收系统资源。

1)newCachedThreadPool

创建一个可缓存线程池,如果线程池长度超过处理需要,可灵活回收空闲线程,如果没有可回收线程,则创建新线程。

优点:

  • 创建线程的数量没有限制(最大为Integer.MAX_VALUE)
  • 如果线程池中没有可执行任务(工作线程空闲了指定的时间,比如1分钟),则该工作线程自动终止。终止后,如果提交了新的任务,则线程池重新创建一个工作线程。
  • 要注意控制线程的数量,不可过多

代码实现:

ExecutorService cachedThreadPool=Executors.newCachedThreadPool();

    for(int i=0;i<20;i++){
        Thread.sleep(i*1000);
        cachedThreadPool.execute(
            new Runnable(){
                public void run(){
                    System.out.println(i);
                }
            }        
    );
   }

2)newFixedThreadPool

创建一个指定工作线程数量的线程池。每提交一次任务就创建一个工作线程,如果工作线程数量达到线程池的最大数,则将提交的任务存入线程池队列中。

优点:

  • 它是一个典型且优秀的线程池,提高程序效率和节省创建线程时所耗的时间开销

缺点:

  • 当线程池中没有可执行任务时,它不会释放工作线程,还会占用一定是系统资源。

代码实现:

ExecutorService fixedThreadPool=Executors.newFixedThreadPool(3);
for(int i=0;i<15;i++){
    fixedThreadPool.execute(new Runnable(){
        public void run(){
            System.out.println(i);
            Thread.sleep(2000);
        }
    }

);

线程池大小设置为3,每个任务输出i后,延迟3秒,所以每3秒输出一个字符。

3)newSingleThreadPool

创建一个单线程的Executo。这个线程池中只有一个工作线程来执行任务,可以保证所有的任务按照指定顺序来执行。如果该线程出现异常,会新建另一个线程取而代之。

优点:保证顺序地执行各个任务,并且在任意时间不会有多个线程是活动的。

代码实现:

ExecutorService singleThreadPool=Executors.newSingleThreadExecutor();

for(int i=0;i<20;i++){
    singleThreadPool.execute(
        new Runnable(){
            public void run(){
                System.out.println(i);
                Thread.sleep(2000);
            }
         }
);

}

4)newScheduleThreadPool

创建一个定长的线程池,同时支持定时任务、定时及周期性任务。

代码实现一个 延时任务

ExecutorService scheduleThreadPool=Executors.newScheduleThreadPool(5);

for(int i=0;i<20;i++){    
     scheduleThreadPool.scheduleAtFixedRate(
        new Runnable(){
            public void run(){
                System.out.println(“延迟3秒钟”);
               
            }
        },3,TimeUnit.SECONDS
);

代码实现一个 定时同时延迟执行:

ExecutorService scheduleThreadPool=Executors.newScheduleThreadPool(5);

for(int i=0;i<20;i++){
   schduleThreadPool.execute(
        new Runnable(){
            public void run(){
                System.out.println("延迟1s,每次执行时间3秒钟");
            }
        },1,3,TimeUnit.SECONDS
        

);

猜你喜欢

转载自blog.csdn.net/weixin_38664232/article/details/83788322