環境資訊中心綜合外電;姜唯 編譯;林大利 審校
本站聲明:網站內容來源環境資訊中心https://e-info.org.tw/,如有侵權,請聯繫我們,我們將及時處理
【其他文章推薦】
※回頭車貨運收費標準
※產品缺大量曝光嗎?你需要的是一流包裝設計!
※自行創業缺乏曝光? 網頁設計幫您第一時間規劃公司的形象門面
※推薦評價好的iphone維修中心
※教你寫出一流的銷售文案?
※台中搬家公司教你幾個打包小技巧,輕鬆整理裝箱!
※台中搬家遵守搬運三大原則,讓您的家具不再被破壞!
居家、公司行號垃圾清運、廢棄物處理、大型家具回收,服務快速,包月及計重或計桶供客戶選擇,合法登記的清潔公司、廢棄物清除許可,專業技術人員及專業廢棄物清運車輛
熱點隨筆:
· Python驗證碼識別 (______null)
· .Net Core 會逆襲成為最受歡迎開發平台嗎? (葡萄城技術團隊)
· 從一年前的1200多人優化到現在200多人,待在這樣的技術團隊是一種什麼體驗? (沛山)
· 字符串太占內存了,我想了各種奇思淫巧對它進行壓縮 (一線碼農)
· 27歲了,程序員寫給自己的一封信 (學習Java的小姐姐)
· 和付費網盤說再見,跟着本文自己起個網盤(Java 開源項目) (削微寒)
· 啪啪,打臉了!領導說:try-catch必須放在循環體外! (Java中文社群)
· 同學叫我一起創業,我不聽,他現在月入10萬,我羡慕死了,我已悟到了成功的秘訣! (jonlan)
· ASP.NET Core Blazor Webassembly 之 數據綁定 (Agile.Zhou)
· MySql輕鬆入門系列——第一站 從源碼角度輕鬆認識mysql整體框架圖 (一線碼農)
· 我終於搞清了啥是 HTTPS 了 (極客挖掘機)
· 六一兒童節,程序員寫給女兒的一封信 (沉默王二)
熱點新聞:
· 月入兩萬的程序員背着電腦送外賣 好隨時改寫代碼
· 《紅警》重製版登上Steam暢銷榜:EA直接放出遊戲源代碼
· 擺攤吧,互聯網人!
· 一鍵“卸載中國應用”這款App,在印度火了
· 鄭皆連院士:中國是橋樑大國卻非橋樑強國 輸在了軟件上
· “刪除中國應用” App被下架,印度人表示氣憤,並喊話劈柴哥出面
· 你常吃的阿莫西林,正在引起一場災難
· 微軟新品被指剽竊!程序員開源兩年的成功項目被迫終結
· 獵鷹與龍飛船基於Linux採用 C++、Chromium與JS開發
· 泥坑裡爬出的任正非
· 唯美的李子柒,世俗的商業化
· 微信支持改 ID 之前,我在好友的微信號里發現了這些秘密
本站聲明:網站內容來源於博客園,如有侵權,請聯繫我們,我們將及時處理
【其他文章推薦】
※自行創業缺乏曝光? 網頁設計幫您第一時間規劃公司的形象門面
※如何讓商品強力曝光呢? 網頁設計公司幫您建置最吸引人的網站,提高曝光率!
※綠能、環保無空污,成為電動車最新代名詞,目前市場使用率逐漸普及化
※廣告預算用在刀口上,台北網頁設計公司幫您達到更多曝光效益
※教你寫出一流的銷售文案?
※別再煩惱如何寫文案,掌握八大原則!
摘錄自2020年5月15日中央社報導
土耳其氣象總局今(14日)就來襲的一波熱浪提出警告,15至19日境內大部分地區可能較正常氣溫高出攝氏9到13度。
「自由日報」(Hurriyet Daily News)報導,包括馬爾馬拉海(Marmara region)、愛琴海、東地中海地區,以及安納托利亞高原(Anatolia)中部部分地區的氣溫,於15至19日間可能會比正常氣溫高出9到13度。
土耳其氣象總局警告,甚至可能會遠遠超過於過去幾年出現的5月高溫紀錄。這一波熱浪將會襲擊全國大部分城巿,伊斯坦堡省長辦公室已就此發布警告。
本站聲明:網站內容來源環境資訊中心https://e-info.org.tw/,如有侵權,請聯繫我們,我們將及時處理
【其他文章推薦】
※廣告預算用在刀口上,台北網頁設計公司幫您達到更多曝光效益
※別再煩惱如何寫文案,掌握八大原則!
※教你寫出一流的銷售文案?
※超省錢租車方案
※廣告預算用在刀口上,台北網頁設計公司幫您達到更多曝光效益
※產品缺大量曝光嗎?你需要的是一流包裝設計!
※回頭車貨運收費標準
摘錄自2020年5月19日自由時報報導
美國國防部已對國會提出一項提案,擴大對稀土的投資上限,以停止對中國的依賴程度,這些稀土可以用來製造飛彈和彈藥、極音速武器,及相關電子產品。如果美國可以重新生產稀土,中國打「稀土牌」的威脅程度將大幅降低。
根據《國防新聞》報導,美國國防部希望提高《國防生產法》的支出上限,在開採稀土上提升至最高17.5億美元(約新台幣523億),在微電子晶片上增至3.5億美元(約新台幣104億),當涉及到極音速武器時,將會沒有上限。據悉,此提案已於本月初提出,已納入國會正在起草的年度國防政策法案。
美國防部副部長洛德(Ellen Lord)去年8月曾表示,國防部正與澳洲進行談判,要求其為美軍提供稀土。澳洲Lynas公司擁有稀土礦,同時在馬來西亞也有精煉廠,可能是此計劃的核心。
本站聲明:網站內容來源環境資訊中心https://e-info.org.tw/,如有侵權,請聯繫我們,我們將及時處理
【其他文章推薦】
※回頭車貨運收費標準
※產品缺大量曝光嗎?你需要的是一流包裝設計!
※自行創業缺乏曝光? 網頁設計幫您第一時間規劃公司的形象門面
※推薦評價好的iphone維修中心
※教你寫出一流的銷售文案?
※台中搬家公司教你幾個打包小技巧,輕鬆整理裝箱!
※台中搬家遵守搬運三大原則,讓您的家具不再被破壞!
其搭載的1。5L地球夢發動機,最大功率131馬力,峰值扭矩155牛米,和CVT變速箱搭配動力響應性出色,加速實力“有點猛”。很好地兼顧了動力以及油耗。空間實用的國貨SUV吉利汽車-遠景SUV指導價:7。49-10。19萬9萬元的預算也可以選擇現在火熱的國產SUV車型,它們空間實用,坐姿高、視野也不錯。
本站聲明:網站內容來源於http://www.auto6s.com/,如有侵權,請聯繫我們,我們將及時處理
【其他文章推薦】
※自行創業缺乏曝光? 網頁設計幫您第一時間規劃公司的形象門面
※如何讓商品強力曝光呢? 網頁設計公司幫您建置最吸引人的網站,提高曝光率!
※綠能、環保無空污,成為電動車最新代名詞,目前市場使用率逐漸普及化
※廣告預算用在刀口上,台北網頁設計公司幫您達到更多曝光效益
※教你寫出一流的銷售文案?
※別再煩惱如何寫文案,掌握八大原則!
一 UML類圖
1.1、ReentrantLock
通過類圖ReentrantLock是同步鎖,同一時間只能有一個線程獲取到鎖,其他獲取該鎖的線程會被阻塞而被放入AQS阻塞隊列中。ReentrantLock類繼承Lock接口;內部抽象類Sync實現抽象隊列同步器AbstractQueuedSynchronizer;Sync類有兩個子類NonfairSync(非公平鎖)和FairSync(公平鎖),默認構造方法使用非公平鎖,可以使用帶布爾參數的構造方法指定使用公平鎖;ReentrantLock可以創建多個條件進行綁定。
1.2、AbstractQueuedSynchronizer
AbstractQueuedSynchronizer:抽象隊列同步器,維護一個volatile int state變量標識共享資源和一個FIFO線程阻塞隊列(AQS隊列)。
protected final void setState(int newState):設置state值
protected final int getState():獲取state值
protected final boolean compareAndSetState(int expect, int update):CAS設置state值
AQS有兩種共享資源類型:SHARED(共享)和EXCLUSIVE(獨佔),針對類型有不同的方法:
protected boolean tryAcquire(int arg):獨佔類型獲取鎖
protected boolean tryRelease(int arg):獨佔類型釋放鎖
protected int tryAcquireShared(int arg):共享類型獲取鎖
protected boolean tryReleaseShared(int arg):共享類型釋放鎖
protected boolean isHeldExclusively():是否是獨佔類型
1.3、線程節點類型waitStatus
AQS隊列中節點的waitStatus枚舉值(java.util.concurrent.locks.AbstractQueuedSynchronizer.Node)含義:
static final int CANCELLED = 1; //線程被取消
static final int SIGNAL = -1; //成功的線程需要被喚醒
static final int CONDITION = -2; //線程在條件隊列中等待
static final int PROPAGATE = -3; //釋放鎖是需要通知其他節點
二 原理分析
2.1 獲取鎖
2.1.1 void lock()方法
調用線程T調用該方法嘗試獲取當前鎖。
①如果鎖未被其他線程獲取,則調用線程T成功獲取到當前鎖,然後設置當前鎖的擁有者為調用線程T,並設置AQS的狀態值state為1,然後直接返回。
②如果調用線程T之前已經獲取當前鎖,則只設置設置AQS的狀態值state加1,然後返回。
③如果當前鎖已被其他線程獲取,則調用線程T放入AQS隊列后阻塞掛起。
public void lock() { sync.lock();//委託內部公平鎖和非公平鎖獲取鎖 }
//非公平鎖
final void lock() { if (compareAndSetState(0, 1))//設置AQS狀態值為1 setExclusiveOwnerThread(Thread.currentThread());//成功設置鎖的線程擁有者 else acquire(1);//失敗加入到AQS隊列阻塞掛起 } //公平鎖 final void lock() { acquire(1); }
非公平鎖分析:
//調用父類AbstractOwnableSynchronizer方法CAS設置state值,成功返回true,失敗返回false protected final boolean compareAndSetState(int expect, int update) { return unsafe.compareAndSwapInt(this, stateOffset, expect, update); } //調用父類AbstractOwnableSynchronizer方法,設置當前線程為鎖的擁有者 protected final void setExclusiveOwnerThread(Thread thread) { exclusiveOwnerThread = thread; }
//調用AbstractQueuedSynchronizer父類方法,第一次獲取鎖失敗 public final void acquire(int arg) { if (!tryAcquire(arg) && acquireQueued(addWaiter(Node.EXCLUSIVE), arg))//排它鎖類型 selfInterrupt(); } //NonfairSync子類,重寫父類方法 protected final boolean tryAcquire(int acquires) { return nonfairTryAcquire(acquires); }
//Sync類非公平鎖嘗試獲取鎖 final boolean nonfairTryAcquire(int acquires) { final Thread current = Thread.currentThread(); int c = getState(); if (c == 0) {//二次獲取鎖 if (compareAndSetState(0, acquires)) { setExclusiveOwnerThread(current); return true; } } else if (current == getExclusiveOwnerThread()) {//當前線程已獲取鎖,AQS狀態值加1 int nextc = c + acquires; if (nextc < 0) // overflow throw new Error("Maximum lock count exceeded"); setState(nextc); return true; } return false; }
//AbstractQueuedSynchronizer類創建節點,添加到AQS隊列後面 private Node addWaiter(Node mode) { Node node = new Node(Thread.currentThread(), mode);//創建AQS隊列的節點,節點類型排它鎖 Node pred = tail;//尾結點 if (pred != null) { node.prev = pred;//新節點的前一個節點是尾結點 if (compareAndSetTail(pred, node)) {//CAS機制添加節點 pred.next = node;//尾結點執行新的節點 return node; } } enq(node); return node; }
//插入節點到隊列中
private Node enq(final Node node) { for (;;) {//循環的方式,直至創建成功 Node t = tail;//尾結點 if (t == null) { //尾結點為空,初始化 if (compareAndSetHead(new Node()))//第一步:CAS創建頭結點(哨兵節點)一個空節點 tail = head; } else { node.prev = t; if (compareAndSetTail(t, node)) {//第二步:CAS設置尾結點 t.next = node; return t; } } } }
// final boolean acquireQueued(final Node node, int arg) { boolean failed = true; try { boolean interrupted = false; for (;;) { final Node p = node.predecessor();//前向節點 if (p == head && tryAcquire(arg)) {//如果p節點是頭結點,node作為隊列第二個節點 setHead(node);//將頭節點設置為node節點,node節點出隊列 p.next = null; //原頭結點設置為空,便於GC回收 failed = false; return interrupted; } if (shouldParkAfterFailedAcquire(p, node) && parkAndCheckInterrupt()) interrupted = true; } } finally { if (failed) cancelAcquire(node);//失敗解鎖 } }
private void setHead(Node node) { head = node; node.thread = null; node.prev = null; }
//阻塞掛起當前線程
static void selfInterrupt() { Thread.currentThread().interrupt(); }
//
private static boolean shouldParkAfterFailedAcquire(Node pred, Node node) { int ws = pred.waitStatus; if (ws == Node.SIGNAL) /* * This node has already set status asking a release * to signal it, so it can safely park. */ return true; if (ws > 0) { /* * Predecessor was cancelled. Skip over predecessors and * indicate retry. */ do { node.prev = pred = pred.prev; } while (pred.waitStatus > 0);//大於0代表線程被取消 pred.next = node; } else { /* * waitStatus must be 0 or PROPAGATE. Indicate that we * need a signal, but don't park yet. Caller will need to * retry to make sure it cannot acquire before parking. */ compareAndSetWaitStatus(pred, ws, Node.SIGNAL); } return false; } //線程阻塞,打斷線程 private final boolean parkAndCheckInterrupt() { LockSupport.park(this); return Thread.interrupted(); }
公平鎖分析:
protected final boolean tryAcquire(int acquires) { final Thread current = Thread.currentThread(); int c = getState(); if (c == 0) { if (!hasQueuedPredecessors() && compareAndSetState(0, acquires)) {//與非公平鎖相比,區別就在標紅的位置 setExclusiveOwnerThread(current); return true; } }else if (current == getExclusiveOwnerThread()) { int nextc = c + acquires; if (nextc < 0) throw new Error("Maximum lock count exceeded"); setState(nextc); return true; } return false; }
public final boolean hasQueuedPredecessors() { // The correctness of this depends on head being initialized // before tail and on head.next being accurate if the current // thread is first in queue. Node t = tail; // Read fields in reverse initialization order Node h = head; Node s;
//①h != t:表示AQS隊列頭結點和尾結點不相同,隊列不為空;
//②(s = h.next) == null || s.thread != Thread.currentThread():頭結點(哨兵節點)為空或者next節點不等於當前線程 return h != t && ((s = h.next) == null || s.thread != Thread.currentThread()); }
2.1.2 void lockInterruptibly()方法
與2.2.1方法相似,不同之處在於:該方法對中斷進行響應,其他線程調用當前線程中斷方法,拋出InterruptedException。
2.1.3 boolean tryLock()方法
嘗試獲取鎖。注意:該方法不會引起當前線程阻塞。
2.1.4 boolean tryLock(long timeout, TimeUnit unit)方法
與2.1.3方法相似,不同之處在於:設置了超時時間。
2.2 釋放鎖
嘗試釋放鎖。
如果當前線程T已獲取鎖,則調用該方法更新AQS狀態值減1。如果當前狀態值為0,則釋放鎖;如果當前狀態值部位0,則只是減1操作。
如果當前線程T未獲取鎖,則調用該方法是會拋出IllegalMonitorStateException異常。
2.2.1 void unlock()方法
public void unlock() { sync.release(1); } //調用AbstractQueuedSynchronizer方法 public final boolean release(int arg) { if (tryRelease(arg)) { Node h = head; if (h != null && h.waitStatus != 0) unparkSuccessor(h);//喚醒線程 return true; } return false; } //回調Sync類釋放鎖 protected final boolean tryRelease(int releases) { int c = getState() - releases; if (Thread.currentThread() != getExclusiveOwnerThread()) throw new IllegalMonitorStateException(); boolean free = false; if (c == 0) { free = true; setExclusiveOwnerThread(null);//設置鎖的擁有線程為空 } setState(c); return free; } // private void unparkSuccessor(Node node) { /* * If status is negative (i.e., possibly needing signal) try * to clear in anticipation of signalling. It is OK if this * fails or if status is changed by waiting thread. */ int ws = node.waitStatus;//線程阻塞等待狀態 if (ws < 0) compareAndSetWaitStatus(node, ws, 0);//CAS設置狀態 /* * Thread to unpark is held in successor, which is normally * just the next node. But if cancelled or apparently null, * traverse backwards from tail to find the actual * non-cancelled successor. */ Node s = node.next; if (s == null || s.waitStatus > 0) { s = null; for (Node t = tail; t != null && t != node; t = t.prev)//遍歷AQS隊列 if (t.waitStatus <= 0) s = t; } if (s != null) LockSupport.unpark(s.thread);//喚醒線程 }
h != t
本站聲明:網站內容來源於博客園,如有侵權,請聯繫我們,我們將及時處理
【其他文章推薦】
※自行創業缺乏曝光? 網頁設計幫您第一時間規劃公司的形象門面
※如何讓商品強力曝光呢? 網頁設計公司幫您建置最吸引人的網站,提高曝光率!
※綠能、環保無空污,成為電動車最新代名詞,目前市場使用率逐漸普及化
※廣告預算用在刀口上,台北網頁設計公司幫您達到更多曝光效益
※教你寫出一流的銷售文案?
※別再煩惱如何寫文案,掌握八大原則!