(java多執行緒併發)控制併發執行緒數的Semaphore
1.簡介
訊號量(Semaphore),有時被稱為訊號燈,是在多執行緒環境下使用的一種設施, 它負責協調各個執行緒, 以保證它們能夠正確、合理的使用公共資源。
2.概念
Semaphore分為單值和多值兩種,前者只能被一個執行緒獲得,後者可以被若干個執行緒獲得。
以一個停車場運作為例。為了簡單起見,假設停車場只有三個車位,一開始三個車位都是空的。這時如果同時來了五輛車,看門人允許其中三輛不受阻礙的進入,然後放下車攔,剩下的車則必須在入口等待,此後來的車也都不得不在入口處等待。這時,有一輛車離開停車場,看門人得知後,開啟車攔,放入一輛,如果又離開兩輛,則又可以放入兩輛,如此往復。
在這個停車場系統中,車位是公共資源,每輛車好比一個執行緒,看門人起的就是訊號量的作用。
更進一步,訊號量的特性如下:訊號量是一個非負整數(車位數),所有通過它的執行緒(車輛)都會將該整數減一(通過它當然是為了使用資源),當該整數值為零時,所有試圖通過它的執行緒都將處於等待狀態。在訊號量上我們定義兩種操作: Wait(等待) 和 Release(釋放)。 當一個執行緒呼叫Wait(等待)操作時,它要麼通過然後將訊號量減一,要麼一直等下去,直到訊號量大於一或超時。Release(釋放)實際上是在訊號量上執行加操作,對應於車輛離開停車場,該操作之所以叫做“釋放”是因為加操作實際上是釋放了由訊號量守護的資源。
在java中,還可以設定該訊號量是否採用公平模式,如果以公平方式執行,則執行緒將會按到達的順序(FIFO)執行,如果是非公平,則可以後請求的有可能排在佇列的頭部。
JDK中定義如下:
Semaphore(int permits, boolean fair)
建立具有給定的許可數和給定的公平設定的Semaphore。
Semaphore當前在多執行緒環境下被擴放使用,作業系統的訊號量是個很重要的概念,在程序控制方面都有應用。Java併發庫Semaphore 可以很輕鬆完成訊號量控制,Semaphore可以控制某個資源可被同時訪問的個數,通過 acquire() 獲取一個許可,如果沒有就等待,而 release() 釋放一個許可。比如在Windows下可以設定共享檔案的最大客戶端訪問個數。
Semaphore實現的功能就類似廁所有5個坑,假如有10個人要上廁所,那麼同時只能有多少個人去上廁所呢?同時只能有5個人能夠佔用,當5個人中 的任何一個人讓開後,其中等待的另外5個人中又有一個人可以佔用了。另外等待的5個人中可以是隨機獲得優先機會,也可以是按照先來後到的順序獲得機會,這取決於構造Semaphore物件時傳入的引數選項。單個訊號量的Semaphore物件可以實現互斥鎖的功能,並且可以是由一個執行緒獲得了“鎖”,再由另一個執行緒釋放“鎖”,這可應用於死鎖恢復的一些場合。
3.案例一:
package SemaPhore;
import java.util.Random;
import java.util.concurrent.*;
public class Test {
public static void main(String[] args) {
//執行緒池
ExecutorService executor = Executors.newCachedThreadPool();
//定義訊號量,只能5個執行緒同時訪問
final Semaphore semaphore = new Semaphore(5);
//模擬20個執行緒同時訪問
for (int i = 0; i < 20; i++) {
final int NO = i;
Runnable runnable = new Runnable() {
public void run() {
try {
//獲取許可
semaphore.acquire();
//availablePermits()指的是當前訊號燈庫中有多少個可以被使用
System.out.println("執行緒" + Thread.currentThread().getName() +"進入,當前已有" + (5-semaphore.availablePermits()) + "個併發");
System.out.println("index:"+NO);
Thread.sleep(new Random().nextInt(1000)*10);
System.out.println("執行緒" + Thread.currentThread().getName() + "即將離開");
//訪問完後,釋放
semaphore.release();
} catch (Exception e) {
e.printStackTrace();
}
}
};
executor.execute(runnable);
}
// 退出執行緒池
executor.shutdown();
}
}
4.案例二:
下面是模擬一個連線池,控制同一時間最多隻能有50個執行緒訪問。
- import java.util.UUID;
- import java.util.concurrent.Semaphore;
- import java.util.concurrent.TimeUnit;
- publicclass TestSemaphore extends Thread {
- publicstaticvoid main(String[] args) {
- int i = 0;
- while (i < 500) {
- i++;
- new TestSemaphore().start();
- try {
- Thread.sleep(1);
- } catch (InterruptedException e) {
- e.printStackTrace();
- }
- }
- }
- /**
- * 控制某資源同時被訪問的個數的類 控制同一時間最後只能有50個訪問
- */
- static Semaphore semaphore = new Semaphore(50);
- staticint timeout = 500;
- publicvoid run() {
- try {
- Object connec = getConnection();
- System.out.println("獲得一個連線" + connec);
- Thread.sleep(300);
- releaseConnection(connec);
- } catch (InterruptedException e) {
- e.printStackTrace();
- }
- }
- publicvoid releaseConnection(Object connec) {
- /* 釋放許可 */
- semaphore.release();
- System.out.println("釋放一個連線" + connec);
- }
- public Object getConnection() {
- try {/* 獲取許可 */
- boolean getAccquire = semaphore.tryAcquire(timeout, TimeUnit.MILLISECONDS);
- if (getAccquire) {
- return UUID.randomUUID().toString();
- }
- } catch (InterruptedException e) {
- e.printStackTrace();
- }
- thrownew IllegalArgumentException("timeout");
- }
- }
相關推薦
(java多執行緒併發)控制併發執行緒數的Semaphore
1.簡介 訊號量(Semaphore),有時被稱為訊號燈,是在多執行緒環境下使用的一種設施, 它負責協調各個執行緒, 以保證它們能夠正確、合理的使用公共資源。 2.概念 Semaph
Java(三)併發控制15.執行緒的優先順序
class PriorityThread extends Thread { public PriorityThread(String name) { super(name); } public void run() { for(int i=0;
執行緒如何控制併發數量? Semaphore 執行緒協同類,用來控制執行緒併發數量
1、 Semaphore:執行緒協同類,用來控制執行緒併發數量,並且可以更加細粒度的進行控制, 因為真正被控制最大併發的程式碼放到了acquire和release之間。 2、主要方法:
JAVA多執行緒(四) Executor併發框架向RabbitMQ推送訊息
github程式碼地址:https://github.com/showkawa/springBoot_2017/tree/master/spb-demo 假設一個需求使用者點選某個頁面,我們後臺需要向MQ推送信資訊 1,模擬的MQ服務,我這邊使用RabbitMQ (關於MQ 傳送和監聽訊息可以
java多執行緒系列翻譯之java併發/多執行緒教程
原文地址:http://tutorials.jenkov.com/java-concurrency/index.html 以前計算機都是單核,同時只能執行一個程式。之後出現了多重任務處理,這意味著計算機同時可以處理多個程式(又名任務或流程)。但這不是真正的“同時執行”,只是單個CPU被多個程式共
JAVA多執行緒和併發面試問題
1. 程序和執行緒之間有什麼不同? 一個程序是一個獨立(self contained)的執行環境,它可以被看作一個程式或者一個應用。而執行緒是在程序中執行的一個任務。Java執行環境是一個包含了不同的類和程式的單一程序。執行緒可以被稱為輕量級程序。執行緒需要較少的資源來建立和駐留在程
總結-Java多執行緒與高併發簡記
1、什麼是多執行緒? 一個程序可以開啟多個執行緒,每個執行緒可以併發/並行執行不同任務。 2、Java多執行緒實現方式 2.1、繼承Thread類 2.2、實現Runnable介面方式實現多執行緒 2.3、使
Java多執行緒-併發之執行緒池
執行緒池有了解嗎? 答: java.util.concurrent.ThreadPoolExecutor 類就是一個執行緒池。客戶端呼叫ThreadPoolExecutor.submit(Runnable task) 提交任務,執行緒池內部維護的工作者執行緒的數量就是該執行緒池的執行
Java多執行緒-併發之synchronized 關鍵字
synchronized 關鍵字 答: 底層實現: 進入時,執行 monitorenter,將計數器 +1,釋放鎖 monitorexit 時,計數器 -1 當一個執行緒判斷到計數器為 0 時,則當前鎖空閒,可以佔用;反之,當前執行緒進入等待狀態 含義
Java多執行緒-併發之sleep() 和 wait(n) 、 wait() 的區別
sleep() 和 wait(n) 、 wait() 的區別 答: sleep 方法:是 Thread 類的靜態方法,當前執行緒將睡眠 n 毫秒,執行緒進入阻塞狀態。當睡眠時間到了,會接觸阻塞,進入可執行狀態,等待 CPU 的到來。睡眠不釋放鎖(如果有的話) wai
Java多執行緒-併發之多執行緒產生死鎖的4個必要條件?如何避免死鎖?
多執行緒產生死鎖的4個必要條件? 答: 互斥條件:一個資源每次只能被一個執行緒使用 請求與保持條件:一個執行緒因請求資源而阻塞時,對已獲得的資源保持不放 不剝奪條件:程序已經獲得的資源,在未使用完之前,不能強行剝奪 迴圈等待條件:若干執行緒之間形成一種頭
Java多執行緒-併發之執行緒和程序的區別
執行緒和程序的區別 答: 程序是一個“執行中的程式”,是系統進行資源分配和排程的一個獨立單位 執行緒是程序的一個實體,一個程序中擁有多個執行緒,執行緒之間共享地址空間和其他資源(所以通訊和同步等操作執行緒比程序更加容易) 執行緒上下文的切換比程序上下文切換要快
Java多執行緒-併發之如何制定多個執行緒的執行順序?
文章目錄 如何讓10個執行緒按照順序列印0123456789? 程式碼如下: 1.建立一個鎖物件類 2.建立一個執行緒類 3.測試類 如何讓10個執行緒按照順序列印012
(CSDN遷移) JAVA多執行緒實現-可控最大併發數執行緒池(newFixedThreadPool)
上篇文章中介紹了單執行緒化執行緒池newSingleThreadExecutor,可控最大併發數執行緒池(newFixedThreadPool)與其最大的區別是可以通知執行多個執行緒,可以簡單的將newSingleThreadExecutor理解為newFixedThreadPool(1)。例如執行一下兩個程
Java多執行緒程式設計核心技術(二)物件及變數的併發訪問
最近一直在忙比賽,四五個吧,時間有點緊張,部落格也沒時間更新~ 只能忙裡抽閒 本文屬於Java多執行緒程式設計系列的第二篇,旨在分享我對多執行緒程式設計技術的心得與感悟,順便做下筆記。 如果你閱讀完比較感興趣,歡迎關注我,等待更新後續篇章。 本文主要介紹Java多執行緒中的同步,也就是如何在Java語言中
java多執行緒面試問答 & java併發面試問答
多執行緒和併發問題是Java技術面試中面試官比較喜歡問的問題之一。在這裡,從面試的角度列出了大部分重要的問題,但是你仍然應該牢固的掌握Java多執行緒基礎知識來對應日後碰到的問題。 Java多執行緒面試問題 1、程序和執行緒之間有什麼不同? 一個程序是一個獨立(self
java多執行緒(含例項)、並行、併發的含義
轉 https://www.cnblogs.com/wxd0108/p/5479442.html 這篇文章寫得非常棒, 我在這裡記錄一下,防止以後找不到了 用多執行緒只有一個目的,那就是更好的利用cpu的資源,因為所有的多執行緒程式碼都可以用單執行緒來
Java 多執行緒高併發 1 — 幾個重要的概念
原子性: 和物理上的原子貌似沒多大關係,對於一系列的操作只能單個執行緒做處理,不能有其他執行緒干擾,例如多個人想往同一個杯子倒茶,但只有一個茶壺,只有等這個茶壺讓出來才能繼續讓其他人倒茶 有序性:
Java 多執行緒高併發 2 — CAS 無鎖
在 Java 併發程式設計裡面,最可愛的就是無鎖了,非常巧妙,精彩絕倫 額。O__O "… 那麼什麼是無鎖? 顧名思義,在併發情況下采用無鎖的方式實現物件操作的原子性,保證資料一致性、安全性、正確性
Java 多執行緒高併發 3.3 — Semaphore 共享鎖使用
Semaphore 是共享鎖的一種,字面上意思就是訊號量鎖 顧名思義,一個可以共享的鎖,可以讓多個執行緒共享同一把鎖,例如同一條馬路可以讓 4 臺車同時並行跑,相當於可以讓 4 個執行緒共享一把鎖,臨