一区二区三区在线-一区二区三区亚洲视频-一区二区三区亚洲-一区二区三区午夜-一区二区三区四区在线视频-一区二区三区四区在线免费观看

服務器之家:專注于服務器技術及軟件下載分享
分類導航

PHP教程|ASP.NET教程|Java教程|ASP教程|編程技術|正則表達式|C/C++|IOS|C#|Swift|Android|VB|R語言|JavaScript|易語言|vb.net|

服務器之家 - 編程語言 - Java教程 - Java 線程池_動力節點Java學院整理

Java 線程池_動力節點Java學院整理

2020-10-30 23:33動力節點 Java教程

系統啟動一個新線程的成本是比較高的,因為它涉及到與操作系統的交互。在這種情況下,使用線程池可以很好的提供性能,尤其是當程序中需要創建大量生存期很短暫的線程時,更應該考慮使用線程池

線程池

系統啟動一個新線程的成本是比較高的,因為它涉及到與操作系統的交互。在這種情況下,使用線程池可以很好的提供性能,尤其是當程序中需要創建大量生存期很短暫的線程時,更應該考慮使用線程池。

與數據庫連接池類似的是,線程池在系統啟動時即創建大量空閑的線程,程序將一個Runnable對象傳給線程池,線程池就會啟動一條線程來執行該對象的run方法,當run方法執行結束后,該線程并不會死亡,而是再次返回線程池中成為空閑狀態,等待執行下一個Runnable對象的run方法。

除此之外,使用線程池可以有效地控制系統中并發線程的數量,但系統中包含大量并發線程時,會導致系統性能劇烈下降,甚至導致JVM崩潰。而線程池的最大線程數參數可以控制系統中并發的線程不超過此數目。

在JDK1.5之前,開發者必須手動的實現自己的線程池,從JDK1.5之后,Java內建支持線程池。

與多線程并發的所有支持的類都在java.util.concurrent包中。我們可以使用里面的類更加的控制多線程的執行。

系統啟動一個新線程的成本是比較高的,因為它涉及到與操作系統的交互。在這種情況下,使用線程池可以很好的提供性能,尤其是當程序中需要創建大量生存期很短暫的線程時,更應該考慮使用線程池

JDK1.5中提供Executors工廠類來產生連接池,該工廠類中包含如下的幾個靜態工程方法來創建連接池:

1、public static ExecutorService newFixedThreadPool(int nThreads):創建一個可重用的、具有固定線程數的線程池。

2、public static ExecutorService newSingleThreadExecutor():創建一個只有單線程的線程池,它相當于newFixedThreadPool方法是傳入的參數為1

3、public static ExecutorService newCachedThreadPool():創建一個具有緩存功能的線程池,系統根據需要創建線程,這些線程將會被緩存在線程池中。

4、public static ScheduledExecutorService newSingleThreadScheduledExecutor:創建只有一條線程的線程池,他可以在指定延遲后執行線程任務

5、public static ScheduledExecutorService newScheduledThreadPool(int corePoolSize):創建具有指定線程數的線程池,它可以再指定延遲后執行線程任務,corePoolSize指池中所保存的線程數,即使線程是空閑的也被保存在線程池內。

上面的幾個方法都有一個重載的方法,多傳入一個ThreadFactory參數的重載方法,使用的比較少。

二、ExecutorService類

可以看到上面的5個方法中,前面3個方法的返回值都是一個ExecutorService對象。該ExecutorService對象就代表著一個盡快執行線程的線程池(只要線程池中有空閑線程立即執行線程任務),程序只要將一個Runnable對象或Callable對象提交給該線程池即可,該線程就會盡快的執行該任務。

ExecutorService有幾個重要的方法:

Java 線程池_動力節點Java學院整理

更詳細的參考JDK API文檔。

submit方法是對 Executor接口execute方法的更好的封裝,建議使用submit方法。

三、ScheduleExecutorService類

在上面的5個方法中,后面2個方法的返回值都是一個ScheduleExecutorService對象。ScheduleExecutorService代表可在指定延遲或周期性執行線程任務的線程池。

ScheduleExecutorService類是ExecutorService類的子類。所以,它里面也有直接提交任務的submit方法,并且新增了一些延遲任務處理的方法:

Java 線程池_動力節點Java學院整理

下面看看線程池的簡單使用:

1、固定大小的線程池:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
package com.bjpowernode.test;
 import java.util.concurrent.ExecutorService;
 import java.util.concurrent.Executors;
 public class PoolTest {
 public static void main(String[] args) {
  ExecutorService pool=Executors.newFixedThreadPool(5);//創建一個固定大小為5的線程池
  for(int i=0;i<7;i++){
  pool.submit(new MyThread());
  }
  pool.shutdown();
 }
 }
 class MyThread extends Thread{
 @Override
 public void run() {
  System.out.println(Thread.currentThread().getName()+"正在執行。。。");
 }
 }

輸出結果:

?
1
2
3
4
5
6
7
pool-1-thread-1正在執行。。。
pool-1-thread-3正在執行。。。
pool-1-thread-2正在執行。。。
pool-1-thread-4正在執行。。。
pool-1-thread-4正在執行。。。
pool-1-thread-5正在執行。。。
pool-1-thread-1正在執行。。。

可以看到雖然我們呢創建了7個MyThread線程對象,但是由于受線程池的大小限制,只是開啟了5個線程,這樣就減少了并發線程的數量。

2、單任務線程池:

?
1
2
3
4
5
6
7
8
9
public class PoolTest {
public static void main(String[] args) {
 ExecutorService pool=Executors.newSingleThreadExecutor();//創建一個單線程池
 for(int i=0;i<7;i++){
 pool.submit(new MyThread());
 }
 pool.shutdown();
}
}

輸出結果:

?
1
2
3
4
5
6
7
pool-1-thread-1正在執行。。。
pool-1-thread-1正在執行。。。
pool-1-thread-1正在執行。。。
pool-1-thread-1正在執行。。。
pool-1-thread-1正在執行。。。
pool-1-thread-1正在執行。。。
pool-1-thread-1正在執行。。。

可以看到,線程池只開啟了一個線程。

3、創建可變尺寸的線程池

?
1
2
3
4
5
6
7
8
9
public class PoolTest {
public static void main(String[] args) {
 ExecutorService pool=Executors.newCachedThreadPool();
 for(int i=0;i<5;i++){
 pool.submit(new MyThread());
 }
 pool.shutdown();
}
}

看輸出結果:

?
1
2
3
4
5
pool-1-thread-1正在執行。。。
pool-1-thread-3正在執行。。。
pool-1-thread-2正在執行。。。
pool-1-thread-4正在執行。。。
pool-1-thread-5正在執行。。。

可以看到,我們沒有限制線程池的大小,但是它會根據需求而創建線程。

4、延遲線程池

?
1
2
3
4
5
6
7
8
9
10
11
12
public class PoolTest {
public static void main(String[] args) {
 ScheduledExecutorService pool=Executors.newScheduledThreadPool(6);
 for(int i=0;i<4;i++){
 pool.submit(new MyThread());
 }
 
 pool.schedule(new MyThread(), 1000, TimeUnit.MILLISECONDS);
 pool.schedule(new MyThread(), 1000, TimeUnit.MILLISECONDS);
 pool.shutdown();
}
}

輸出結果:

?
1
2
3
4
5
6
pool-1-thread-1正在執行。。。
pool-1-thread-3正在執行。。。
pool-1-thread-2正在執行。。。
 pool-1-thread-4正在執行。。。
 pool-1-thread-6正在執行。。。
pool-1-thread-1正在執行。。。

可以明顯看到,最后兩個線程不是立即執行,而是延遲了1秒在執行的。

5、單任務延遲線程池

?
1
2
3
4
5
6
7
8
9
10
11
12
public class PoolTest {
public static void main(String[] args) {
 ScheduledExecutorService pool=Executors.newSingleThreadScheduledExecutor();
 for(int i=0;i<4;i++){
 pool.submit(new MyThread());
 }
 
 pool.schedule(new MyThread(), 1000, TimeUnit.MILLISECONDS);
 pool.schedule(new MyThread(), 1000, TimeUnit.MILLISECONDS);
 pool.shutdown();
}
}

上面我們使用的是JDK幫我封裝好的線程池,我們也可以自己定義線程池,查看源碼,我們發現,Excutors里面的獲得線程的靜態方法,內部都是調用ThreadPoolExecutor的構造方法。比如:

?
1
2
3
4
5
6
public static ExecutorService newFixedThreadPool(int nThreads, ThreadFactory threadFactory) {
return new ThreadPoolExecutor(nThreads, nThreads,
    0L, TimeUnit.MILLISECONDS,
    new LinkedBlockingQueue<Runnable>(),
    threadFactory);
}

可以看到,它是通過調用ThreadPoolExecutor的構造方法來返回一個線程池的。所以,我們也可以自己手動的調用ThreadPoolExecutor的各種構造方法,來定義自己的線程池規則,不過一般情況下,使用自帶的線程池就夠了,不需要自己來實現。

以上所述是小編給大家介紹的Java 線程池,希望對大家有所幫助,如果大家有任何疑問請給我留言,小編會及時回復大家的。在此也非常感謝大家對服務器之家網站的支持!

延伸 · 閱讀

精彩推薦
主站蜘蛛池模板: 经典千人斩一区二区视频 | 国产精品免费视频能看 | 国产欧美日韩成人 | 久久亚洲精品AV成人无 | 91香蕉依人综合久久 | 秋霞在线一级 | 欧美在线观看网址 | 美女奶口隐私免费视频网站 | 亚洲AV午夜福利精品香蕉麻豆 | avtt在线播放 | 天天爽天天干天天操 | 久久国产精品免费网站 | 国产成人免费在线视频 | 欧美成年黄网站色高清视频 | 国产美女做爰免费视频软件 | 精品蜜臀AV在线天堂 | 国产香蕉一区二区在线观看 | 91制片厂制作传媒免费版樱花 | 国产精品毛片高清在线完整版 | 美女露尿口 | 国产麻豆91欧美一区二区 | 国产情侣视频观看 | 日韩在线一区二区 | 操老妇| 亚洲视频1区 | 日本黄a三级三级三级 | 91av手机在线 | 欧美大片一区 | 国产午夜视频在线观看网站 | 日本高清免费不卡在线 | 办公室强行丝袜秘书啪啪 | 国产主播福利在线观看 | 九九99香蕉在线视频免费 | 久久亚洲网站 | 11 13加污女qq看他下面 | a级免费在线观看 | 99在线观看视频免费精品9 | 99热碰 | 四虎精品成人免费视频 | 4444亚洲国产成人精品 | 99在线视频精品 |