4种线程池的创建方式

在线程池里面创建线程,使用线程池可以很好地提高性能,程序将一个任务传给线程池,线程池就会启动一条线程来执行这个任务,执行结束以后,该线程并不会死亡,而是再次返回线程池中成为空闲状态,等待执行下一个任务。
4种线程池均用Executors创建:
  • Executors.newCacheThreadPool()
按需创建新的线程,先查看池中有没有以前建立的线程,如果有,就重用。如果没有,就建一个新的线程加入池中,通常用于执行一些生存期很短的任务
public class ThreadPoolExecutorTest {
     public static void main(String[] args) {
          //创建一个线程池
         ExecutorService cachedThreadPool = Executors.newCachedThreadPool();
         for (int i = 0; i < 10; i++) {
         Thread.sleep(1000);//每隔一秒创建一个线程
             cachedThreadPool.execute(new Runnable() {
                 public void run() {
                 //打印正在执行的缓存线程信息
                 System.out.println(Thread.currentThread().getName()+"正在被执行");
                 }
           });
         }
     }
 }
  •  Executors.newFixedThreadPool(int n)
创建一个线程池,该线程池可并发执行的线程数固定,某一线程执行完当前任务后该线程可以被重用执行另外一任务,线程池n个线程都被占用时,其他 任务按照任务的提交顺序在队列中等待
 public class ThreadPoolExecutorTest {
       public static void main(String[] args) {
        //创建一个可重用固定个数的线程池
        ExecutorService fixedThreadPool = Executors.newFixedThreadPool(3);
        for (int i = 0; i < 10; i++) {
                 fixedThreadPool.execute(new Runnable() {      //很厉害的匿名内部类
                 public void run() {
                 try {
                   //打印正在执行的缓存线程信息
                  System.out.println(Thread.currentThread().getName()+"正在被执行");
                         Thread.sleep(2000);     //每隔2秒轮流打印3个线程的名字
                     } catch (InterruptedException e) {
                        e.printStackTrace();
                     }
                  }
             });
         }
     }
 }

 
  • Executors.newSingleThreadExecutor()
创建一个只有单线程的线程池,它只会用唯一的线程来执行任务, 如果这个唯一的线程因为异常结束,那么会有一个新的线程来替代它,此线程池保证所有任务的执行顺序按照任务的提交顺序执行
public class TestThreadPoolExecutor {
      public static void main(String[] args) {
          //创建一个单线程化的线程池
          ExecutorService singleThreadExecutor =   
                        Executors.newSingleThreadExecutor();
          for (int i = 0; i < 10; i++) {
            /*index为不可变量,每一次for循环后本次final变量出了这个块的作用域范围就            
              会失效,下次循环的时候重建一个不同域的final变量,故不同域对应的线程使用
              不同的index*/
             final int index = i;
             singleThreadExecutor.execute(new Runnable() {
             public void run() {
             try {
                  //结果依次输出,相当于顺序执行各个任务
                   System.out.println(Thread.currentThread().getName()+"正在被执
                                                行,打印的值是:"+index);
                         Thread.sleep(1000);
                     } catch (InterruptedException e) {
                         e.printStackTrace();
                     }
                 }
             });
         }
     }
 }                            
                              
                        
 
  • Executors.newScheduledThreadPool(int n)
创建一个定长线程池,线程池里面的任务执行又分两种:定时或者周期性执行
  1. 定时执行
public class ThreadPoolExecutorTest {
      public static void main(String[] args) {
          //创建一个定长线程池,支持定时及周期性任务执行——延迟执行
         ScheduledExecutorService scheduledThreadPool =     
         Executors.newScheduledThreadPool(5);
         //延迟1秒执行
         scheduledThreadPool.schedule(new Runnable() {
             public void run() {
                 System.out.println("延迟1秒执行");
            }
         }, 1, TimeUnit.SECONDS);//1秒后执行一次即over
     }
}    
  1. 周期性执行
public class ThreadPoolExecutorTest {
         public static void main(String[] args) {
          //创建一个定长线程池,支持定时及周期性任务执行——定期执行
         ScheduledExecutorService scheduledThreadPool =     
                            Executors.newScheduledThreadPool(5);
         /*延迟1秒后执行该任务,以后每隔3秒再次执行该任务,每隔3秒若上次任务已完成则
            启动本次任务,否则等上次任务结束后才启动本次任务(尽管已经到了3秒)*/
         scheduledThreadPool.scheduleAtFixedRate(new Runnable() {
         public void run() {
                 System.out.println("延迟1秒后再每3秒执行一次");
             }
         }, 1, 3, TimeUnit.SECONDS);
     }
 }                

 
 

猜你喜欢

转载自www.cnblogs.com/afei1759/p/11080583.html