線程池
六、線程池
前言:在以前創建一個線程時,總是要手動創建一個線程,然後啓動運行;並且一旦線程運行結束後,就作廢;當要運行的線程數過多時,這種創建方式的弊端便會很明顯。就好比一個公司接待客戶,當每個客戶需要服務時,就去招聘一個員工來給該客戶服務,當服務完畢後就解僱該員工,這顯然不符合客觀事實。同理,當線程數過多時,傳統的創建線程方式有侷限性。
在JDK1.5版本以後,Java提供了線程池,對應的API爲Executors,創建一個線程池時,可以指定裏面含有幾個線程。當要執行某些任務時,可以直接把這些任務放到線程池中,即可。線程池會按照它容量的大小循環執行完這些任務。就好比一個公司中有固定的員工數量,不管來了多少的客戶,只要該公司的員工有空,都會去接待這些客戶,當員工沒空時,客戶等待,這就提高了一個員工的使用次數,同理,線程池中的線程也可以使用多次。
在線程池的編程模式下,任務是提交給整個線程池,而不是直接交給某個線程,線程池在拿到任務後,它就在內部找有無空閒的線程,再把任務交給內部某個空閒的線程,這就是封裝。任務是提交給整個線程池,一個線程同時只能執行一個任務,但可以同時向一個線程池提交多個任務。
更多詳細的介紹請查閱API文檔,在此只做大概的介紹,下面代碼體現:
package itheima.thread.day01;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;
public class ThreadPoolTest {
public static void main(String[] args) {
// 工具類一般帶s,裏面提供一大堆靜態方法
// 固定線程數的線程池
// ExecutorService threadPool= Executors.newFixedThreadPool(3);
// 帶緩衝的線程池
// ExecutorService threadPool= Executors.newCachedThreadPool();
// 創建單獨的一個線程,沒有池的概念
ExecutorService threadPool= Executors.newSingleThreadExecutor();
// 線程池中只有三個線程,只能三個服務完了才服務其他的線程
for(int i=1;i<=10;i++){
final int task = i;
threadPool.execute(new Runnable(){
@Override
public void run() {
for(int j=1;j<=10;j++){
try {
Thread.sleep(20);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(Thread.currentThread().getName()+" loop of "+j+" for task of "+task);
}
}
});
}
// 關閉線程池中的所有線程
// threadPool.shutdown();
// 定時器
// Executors.newScheduledThreadPool(3).schedule(
Executors.newScheduledThreadPool(3).scheduleAtFixedRate(
new Runnable() {
@Override
public void run() {
System.out.println("bombing......");
}
},
2,
3,
TimeUnit.SECONDS);
}
}