www.久久久久|狼友网站av天堂|精品国产无码a片|一级av色欲av|91在线播放视频|亚洲无码主播在线|国产精品草久在线|明星AV网站在线|污污内射久久一区|婷婷综合视频网站

當(dāng)前位置:首頁(yè) > 公眾號(hào)精選 > 架構(gòu)師社區(qū)
[導(dǎo)讀]國(guó)慶的時(shí)候閑來(lái)無(wú)事,就隨手寫(xiě)了一點(diǎn)之前說(shuō)的比賽的代碼,目標(biāo)就是保住前100混個(gè)大賽的文化衫就行了?,F(xiàn)在還混在前50的隊(duì)伍里面,穩(wěn)的一比。其實(shí)我覺(jué)得大家做柔性負(fù)載均衡那題的思路其實(shí)都不會(huì)差太多,就看誰(shuí)能把關(guān)鍵的信息收集起來(lái)并利用上了。由于是基于Dubbo去做的嘛,調(diào)試的過(guò)程中,寫(xiě)著...


國(guó)慶的時(shí)候閑來(lái)無(wú)事,就隨手寫(xiě)了一點(diǎn)之前說(shuō)的比賽的代碼,目標(biāo)就是保住前 100 混個(gè)大賽的文化衫就行了。

現(xiàn)在還混在前 50 的隊(duì)伍里面,穩(wěn)的一比。

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
其實(shí)我覺(jué)得大家做柔性負(fù)載均衡那題的思路其實(shí)都不會(huì)差太多,就看誰(shuí)能把關(guān)鍵的信息收集起來(lái)并利用上了。

由于是基于 Dubbo 去做的嘛,調(diào)試的過(guò)程中,寫(xiě)著寫(xiě)著我看到了這個(gè)地方:

org.apache.dubbo.rpc.protocol.AbstractInvoker#waitForResultIfSync

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
先看我框起來(lái)的這一行代碼,aysncResult 的里面有有個(gè) CompletableFuture ,它調(diào)用的是帶超時(shí)時(shí)間的 get() 方法,超時(shí)時(shí)間是 Integer.MAX_VALUE,理論上來(lái)說(shuō)效果也就等同于 get() 方法了。

從我直觀(guān)上來(lái)說(shuō),這里用 get() 方法也應(yīng)該是沒(méi)有任何毛病的,甚至更好理解一點(diǎn)。

但是,為什么沒(méi)有用 get() 方法呢?

其實(shí)方法上的注釋已經(jīng)寫(xiě)到原因了,就怕我這樣的人產(chǎn)生了這樣的疑問(wèn):

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
抓住我眼球的是這這幾個(gè)單詞:

have serious performance drop。

性能?chē)?yán)重下降。

大概就是說(shuō)我們必須要調(diào)用 java.util.concurrent.CompletableFuture#get(long, java.util.concurrent.TimeUnit) 而不是 get() 方法,因?yàn)?get 方法被證明會(huì)導(dǎo)致性能?chē)?yán)重的下降。

對(duì)于 Dubbo 來(lái)說(shuō), waitForResultIfSync 方法,是主鏈路上的方法。

我個(gè)人覺(jué)得保守一點(diǎn)說(shuō),可以說(shuō) 90% 以上的請(qǐng)求都會(huì)走到這個(gè)方法來(lái),阻塞等待結(jié)果。所以如果該方法如果有問(wèn)題,則會(huì)影響到 Dubbo 的性能。

Dubbo 作為中間件,有可能會(huì)運(yùn)行在各種不同的 JDK 版本中,對(duì)于特定的 JDK 版本來(lái)說(shuō),這個(gè)優(yōu)化確實(shí)是對(duì)于性能的提升有很大的幫助。

就算不說(shuō) Dubbo ,我們用到 CompletableFuture 的時(shí)候,get() 方法也算是我們常常會(huì)用到的一個(gè)方法。

另外,這個(gè)方法的調(diào)用鏈路我可太熟悉了。

因?yàn)槲覂赡昵皩?xiě)的第一篇公眾號(hào)文章就是探討 Dubbo 的異步化改造的。

當(dāng)年,這部分代碼肯定不是這樣的,至少?zèng)]有這個(gè)提示。

因?yàn)槿绻羞@個(gè)提示的話(huà),我肯定第一次寫(xiě)的時(shí)候就注意到了。

果然,我去翻了一下,雖然圖片已經(jīng)很模糊了,但是還是能隱約看到,之前確實(shí)是調(diào)用的 get() 方法:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!

我還稱(chēng)之為最“騷”的一行代碼。

因?yàn)檫@一行的代碼就是 Dubbo 異步轉(zhuǎn)同步的關(guān)鍵代碼。

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
前面只是一個(gè)引子,本文不會(huì)去寫(xiě) Dubbo 相關(guān)的知識(shí)點(diǎn)。

主要寫(xiě)寫(xiě) CompletableFuture 的 get() 到底有啥問(wèn)題。

放心,這個(gè)點(diǎn)面試肯定不考。

只是你知道這個(gè)點(diǎn)后,恰好你的 JDK 版本是沒(méi)有修復(fù)之前的,寫(xiě)代碼的時(shí)候可以稍微注意一下。

學(xué) Dubbo 在方法調(diào)用的地方加上一樣的 NOTICE,直接把逼格拉滿(mǎn)。等著別人問(wèn)起來(lái)的時(shí)候,你再娓娓道來(lái)。

或者不經(jīng)意間看到別人這樣寫(xiě)的時(shí)候,輕飄飄的說(shuō)一句:這里有可能會(huì)有性能問(wèn)題,可以去了解一下。

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!

啥性能問(wèn)題?

根據(jù) Dubbo 注釋里面的這點(diǎn)信息,我也不知道啥問(wèn)題,但是我知道去哪里找問(wèn)題。

這種問(wèn)題肯定在 openJDK 的 bug 列表里面記錄有案,所以第一站就是來(lái)這里搜索一下關(guān)鍵字:

https://bugs.openjdk.java.net/projects/JDK/issues/

一般來(lái)說(shuō),都是一些陳年老 BUG,需要搜索半天才能找到自己想要的信息。

但是,這次運(yùn)氣好到爆棚,彈出來(lái)的第一個(gè)就是我要找的東西,簡(jiǎn)直是搞的我都有點(diǎn)不習(xí)慣了,這難道是傳說(shuō)中的國(guó)慶獻(xiàn)禮嗎,不敢想不敢想。

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
標(biāo)題就是:對(duì)CompletableFuture的性能改進(jìn)。

里面提到了編號(hào)為 8227019 的 BUG。

https://bugs.openjdk.java.net/browse/JDK-8227019

我們一起看看這個(gè) BUG 描述的是啥玩意。

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
標(biāo)題翻譯過(guò)來(lái),大概意思就是說(shuō) CompletableFuture.waitingGet 方法里面有一個(gè)循環(huán),這個(gè)循環(huán)里面調(diào)用了 Runtime.availableProcessors 方法。且這個(gè)方法被調(diào)用的很頻繁,這樣不好。

在詳細(xì)描述里面,它提到了另外的一個(gè)編號(hào)為 8227006 的 BUG,這個(gè) BUG 描述的就是為什么頻繁調(diào)用 availableProcessors 不太好,但是這個(gè)我們先按下不表。

先研究一下他提到的這樣一行代碼:

?spins?=?(Runtime.getRuntime().availableProcessors()?>?1)??
????????????????????1?<
他說(shuō)位于 waitingGet 里面,我們就去看看到底是怎么回事嘛。

但是我本地的 JDK 的版本是 1.8.0_271,其 waitingGet 源碼是這樣的:

java.util.concurrent.CompletableFuture#waitingGet

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
先不管這幾行代碼是啥意思吧,反正我發(fā)現(xiàn)沒(méi)有看到 bug 中提到的代碼,只看到了 spins=SPINS ,雖然 SPINS 調(diào)用了 Runtime.getRuntime().availableProcessors() 方法,但是該字段被 static 和 final 修飾了,也就不存在 BUG 中描述的“頻繁調(diào)用”了。

于是我意識(shí)到我的版本是不對(duì)的,這應(yīng)該是被修復(fù)之后的代碼,所以去下載了幾個(gè)之前的版本。

最終在 JDK 1.8.0_202 版本中找到了這樣的代碼:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
和前面截圖的源碼的差異就在于前者多了一個(gè) SPINS 字段,把 Runtime.getRuntime().availableProcessors() 方法的返回緩存了起來(lái)。

我一定要找到這行代碼的原因就是要證明這樣的代碼確實(shí)是在某些 JDK 版本中出現(xiàn)過(guò)。

好了,現(xiàn)在我們看一下 waitingGet 方法是干啥的。

首先,調(diào)用 get() 方法的時(shí)候,如果 result 還是 null 那么說(shuō)明異步線(xiàn)程執(zhí)行的結(jié)果還沒(méi)就緒,則調(diào)用 waitingGet 方法:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
而來(lái)到 waitingGet 方法,我們只關(guān)注 BUG 相關(guān)這兩個(gè)分支判斷:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
首先把 spins 的值初始化為 -1。

然后當(dāng) result 為 null 的時(shí)候,就一直進(jìn)行 while 循環(huán)。

所以,如果進(jìn)入循環(huán),第一次一定會(huì)調(diào)用 availableProcessors 方法。然后發(fā)現(xiàn)是多處理器的運(yùn)行環(huán)境,則把 spins 置為 1<<8 ,即 256。

然后再次進(jìn)行循環(huán),走入到 spins>0 的分支判斷,接著做一個(gè)隨機(jī)運(yùn)算,隨機(jī)出來(lái)的值如果大于等于 0 ,則對(duì) spins 進(jìn)行減一操作。

只有減到 spins 為 0 的時(shí)候才會(huì)進(jìn)入到后面的這些被我框起來(lái)的邏輯中:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
也就是說(shuō)這里就是把 spins 從 256 減到 0,且由于隨機(jī)函數(shù)的存在,循環(huán)次數(shù)一定是大于 256 次的。

但是還有一個(gè)大前提,那就是每次循環(huán)的時(shí)候都會(huì)去判斷循環(huán)條件是否還成立。即判斷 result 是否還是 null。為 null 才會(huì)繼續(xù)往下減。

所以,你說(shuō)這段代碼是在干什么事兒?

其實(shí)注釋上已經(jīng)寫(xiě)的很清楚了:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
Use brief spin-wait on multiprocessors。

brief,這是一個(gè)四級(jí)詞匯哈,得記住,要考的。就是“短暫”的意思,是一個(gè)不規(guī)則動(dòng)詞,其最高級(jí)是 briefest。

對(duì)了,spin 這個(gè)單詞大家應(yīng)該認(rèn)識(shí)吧,前面忘記給大家教單詞了,就一起講了,看小黑板:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
所以注釋上說(shuō)的就是:如果是多處理器,則使用短暫的自旋等待一下。

從 256 減到 0 的過(guò)程,就是這個(gè)“brief spin-wait”。

但是仔細(xì)一想,在自旋等待的這個(gè)過(guò)程中,availableProcessors 方法只是在第一次進(jìn)入循環(huán)的時(shí)候調(diào)用了一次。

那為什么說(shuō)它耗費(fèi)性能呢?

是的,確實(shí)是調(diào)用 get() 方法的只調(diào)用了一次,但是你架不住 get() 方法被調(diào)用的次數(shù)多啊。

就拿 Dubbo 舉例,絕大部分情況下的大家的調(diào)用方式都用的是默認(rèn)的同步調(diào)用的方案。所以每一次調(diào)用都會(huì)到異步轉(zhuǎn)同步這里阻塞等待結(jié)果,也就說(shuō)每次都會(huì)調(diào)用一次 get() 方法,即 availableProcessors 方法就會(huì)被調(diào)用一次。

那么解決方案是什么呢?

在前面我已經(jīng)給大家看了,就是把 availableProcessors 方法的返回值找個(gè)字段給緩存起來(lái):

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
但是后面跟了一個(gè)“problem”。

這個(gè)“problem”就是說(shuō)如果我們把多處理器這個(gè)值緩存起來(lái)了,假設(shè)程序運(yùn)行的過(guò)程中出現(xiàn)了從多處理器到單處理器的運(yùn)行環(huán)境變化這個(gè)值就不準(zhǔn)確了,雖然這是一個(gè)不太可能的變化。但是即使這個(gè)“problem”真的發(fā)生了也沒(méi)有關(guān)系,它只是會(huì)導(dǎo)致一個(gè)小小的性能損失。

所以就出現(xiàn)了前面大家看到的這樣的代碼,這就是 “we can cache this value in a field”:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
而體現(xiàn)到具體的代碼變更是這樣的:

http://cr.openjdk.java.net/~shade/8227018/webrev.01/src/share/classes/java/util/concurrent/CompletableFuture.java.udiff.html

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
所以,當(dāng)你去看這部分源碼的時(shí)候,你會(huì)看到 SPINS 字段上其實(shí)還有很長(zhǎng)一段話(huà),是這樣的:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
給大家翻譯一下:

1.在 waitingGet 方法中,進(jìn)行阻塞操作前,進(jìn)行旋轉(zhuǎn)。

2.沒(méi)有必要在單處理器上進(jìn)行旋轉(zhuǎn)。

3.調(diào)用 Runtime.availableProcessors 方法的成本是很高的,所以在此緩存該值。但是這個(gè)值是首次初始化時(shí)可用的 CPU 的數(shù)量。如果某系統(tǒng)在啟動(dòng)時(shí)只有一個(gè) CPU 可以用,那么 SPINS 的值會(huì)被初始化為 0,即使后面再使更多的 CPU 在線(xiàn),也不會(huì)發(fā)生變化。

當(dāng)你有了前面的 BUG 的描述中的鋪墊之后,你就明白了為什么這里寫(xiě)上了這么一大段話(huà)。

有的同學(xué)就真的去翻代碼,也許你看到的是這樣的:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
什么情況?根本就看不到 SPINS 相關(guān)的代碼啊,這不是欺騙老實(shí)人嗎?

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!

你別慌啊,猴急猴急的,我這不是還沒(méi)說(shuō)完嘛?

我們?cè)侔涯抗夥诺綀D片中的這句話(huà)上:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
只需要在 JDK 8 中進(jìn)行這個(gè)修復(fù)即可,因?yàn)?JDK 9 和更高版本的代碼都不是這樣的寫(xiě)的了。

比如在 JDK 9 中,直接拿掉了整個(gè) SPINS 的邏輯,不要這個(gè)短暫的自旋等待了:

http://hg.openjdk.java.net/jdk9/jdk9/jdk/rev/f3af17da360b

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
雖然,拿掉了這個(gè)短暫的自旋等待,但是其實(shí)也算是學(xué)習(xí)了一個(gè)騷操作。

比如怎么在不引入時(shí)間的前提下,做出一個(gè)自旋等待的效果?

答案就是被拿掉的這段代碼。

但是有一說(shuō)一,我第一次看到這個(gè)代碼的時(shí)候我就覺(jué)得別扭。這一個(gè)短短的自旋能延長(zhǎng)多少時(shí)間呢?

加入這個(gè)自旋,是為了稍晚一點(diǎn)執(zhí)行后續(xù)邏輯中的 park 代碼,這個(gè)稍重一點(diǎn)的操作。但是我覺(jué)得這個(gè) “brief spin-wait” 的收益其實(shí)是微乎其微的。

所以我也理解為什么后續(xù)直接把這一整坨代碼拿掉了。而拿掉這一坨代碼的時(shí)候,其實(shí)作者并沒(méi)有意識(shí)到這里有 BUG。

這里提到的作者,其實(shí)就是 Doug Lea 老爺子。

我為什么敢這樣說(shuō)呢?

那必然是有證據(jù)的呀。

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!

依據(jù)就在這個(gè) BUG 鏈接里面提到的編號(hào)為 8227018 的 BUG 中,它們其實(shí)描述的是同一個(gè)事情:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
這里面有這樣一段對(duì)話(huà),出現(xiàn)了 David Holmes 和 Doug Lea:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
Holmes 在這里面提到了 “cache this value in a field” 的解決方案,并得到了 Doug 的同意。

Doug 說(shuō):JDK 9 已經(jīng)不用 spin 了。

所以,我個(gè)人理解是 Doug 在不知道這個(gè)地方有 BUG 的情況下,拿掉了 SPIN 的邏輯。至于是出于什么考慮,我猜測(cè)是收益確實(shí)不大,且代碼具有一定的迷惑性。還不如拿掉之后,理解起來(lái)直觀(guān)一點(diǎn)。

Doug Lea 大家都耳熟能詳, David Holmes 是誰(shuí)呢?

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!

《Java 并發(fā)編程實(shí)戰(zhàn)》的作者之一,端茶就完事了。

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
而你要是對(duì)我以前的文章印象足夠深刻,那么你會(huì)發(fā)現(xiàn)早在《Doug Lea在J.U.C包里面寫(xiě)的BUG又被網(wǎng)友發(fā)現(xiàn)了?!愤@篇文章里面,他就已經(jīng)出現(xiàn)過(guò)了:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
老朋友又出現(xiàn)了,建議鐵汁們把夢(mèng)幻聯(lián)動(dòng)打在公屏上。

到底啥原因?

前面噼里啪啦的說(shuō)了這么大一段,核心思想其實(shí)就是 Runtime.availableProcessors 方法的調(diào)用成本高,所以在 CompletableFuture.waitingGet 方法中不應(yīng)該頻繁調(diào)用這個(gè)方法。

但是 availableProcessors 為什么調(diào)用成本就高了,依據(jù)是啥,得拿出來(lái)看看?。?/p>這一小節(jié),就給大家看看依據(jù)是什么。

依據(jù)就在這個(gè) BUG 描述中:

https://bugs.openjdk.java.net/browse/JDK-8157522

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
標(biāo)題上說(shuō):在 linux 環(huán)境下,Runtime.availableProcessors 執(zhí)行時(shí)間增加了 100 倍。

增加了 100 倍,肯定是有兩個(gè)不同的版本的對(duì)比,那么是哪兩個(gè)版本呢?

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
在 1.8b191 之前的 JDK 版本上,下面的示例程序可以實(shí)現(xiàn)每秒 400 多萬(wàn)次對(duì) Runtime.availableProcessors 的調(diào)用。

但在 JDK build 1.8b191 和所有后來(lái)的主要和次要版本(包括11)上,它能實(shí)現(xiàn)的最大調(diào)用量是每秒4萬(wàn)次左右,性能下降了100倍。

這就導(dǎo)致了 CompletableFuture.waitingGet 的性能問(wèn)題,它在一個(gè)循環(huán)中調(diào)用了 Runtime.availableProcessors。因?yàn)槲覀兊膽?yīng)用程序在異步代碼中表現(xiàn)出明顯的性能問(wèn)題,waitingGet 就是我們最初發(fā)現(xiàn)問(wèn)題的地方。

測(cè)試代碼是這樣的:

??public?static?void?main(String[]?args)?throws?Exception?{
????????AtomicBoolean?stop?=?new?AtomicBoolean();
????????AtomicInteger?count?=?new?AtomicInteger();

????????new?Thread(()?->?{
????????????while?(!stop.get())?{
????????????????Runtime.getRuntime().availableProcessors();
????????????????count.incrementAndGet();
????????????}
????????}).start();

????????try?{
????????????int?lastCount?=?0;
????????????while?(true)?{
????????????????Thread.sleep(1000);
????????????????int?thisCount?=?count.get();
????????????????System.out.printf("%s?calls/sec%n",?thisCount?-?lastCount);
????????????????lastCount?=?thisCount;
????????????}
????????}
????????finally?{
????????????stop.set(true);
????????}
????}
按照 BUG 提交者的描述,如果你在 64 位的 Linux 上,分別用 JDK 1.8b182 和 1.8b191 版本去跑,你會(huì)發(fā)現(xiàn)有近 100 倍的差異。

至于為什么有 100 倍的性能差異,一位叫做 Fairoz Matte 的老哥說(shuō)他調(diào)試了一下,定位到問(wèn)題出現(xiàn)在調(diào)用 “OSContainer::is_containerized()” 方法的時(shí)候:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
而且他也定位到了問(wèn)題出現(xiàn)的最開(kāi)始的版本號(hào)是 8u191 b02,在這個(gè)版本之后的代碼都會(huì)有這樣的問(wèn)題。

帶來(lái)問(wèn)題的那次版本升級(jí)干的事是改進(jìn) docker 容器檢測(cè)和資源配置的使用。

所以,如果你的 JDK 8 是 8u191 b02 之前的版本,且系統(tǒng)調(diào)用并發(fā)非常高,那么恭喜你,有機(jī)會(huì)踩到這個(gè)坑。

然后,下面幾位大佬基于這個(gè)問(wèn)題給出了很多解決方案,并針對(duì)各種解決方案進(jìn)行討論。

有的解決方案,聽(tīng)起來(lái)就感覺(jué)很麻煩,需要編寫(xiě)很多的代碼,我就不一一解讀了。

最終,大道至簡(jiǎn),還是選擇了實(shí)現(xiàn)起來(lái)比較簡(jiǎn)單的 cache 方案,雖然這個(gè)方案也有一點(diǎn)瑕疵,但是出現(xiàn)的概率非常低且是可以接受的。

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!

再看get方法

現(xiàn)在我們知道了這個(gè)沒(méi)有卵用的知識(shí)點(diǎn)之后,我們?cè)倏纯礊槭裁凑{(diào)用帶超時(shí)時(shí)間的 get() 方法,沒(méi)有這個(gè)問(wèn)題。

java.util.concurrent.CompletableFuture#get(long, java.util.concurrent.TimeUnit)

首先可以看到內(nèi)部調(diào)用的方法都不一樣了:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
有超時(shí)時(shí)間的 get() 方法,內(nèi)部調(diào)用的是 timedGet 方法,入?yún)⒕褪浅瑫r(shí)時(shí)間。

點(diǎn)進(jìn) timedGet 方法就知道為什么調(diào)用帶超時(shí)時(shí)間的 get() 方法沒(méi)有問(wèn)題了:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
在代碼的注釋里面已經(jīng)把答案給你寫(xiě)好了:我們故意不在這里旋轉(zhuǎn)(像waitingGet那樣),因?yàn)樯厦鎸?duì) nanoTime() 的調(diào)用很像一個(gè)旋轉(zhuǎn)。

可以看到在該方法內(nèi)部,根本就沒(méi)有對(duì) Runtime.availableProcessors 的調(diào)用,所以也就不存在對(duì)應(yīng)的問(wèn)題。

現(xiàn)在,我們回到最開(kāi)始的地方:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
那么你說(shuō),下面的 asyncResult.get(Integer.MAX_VALUE, TimeUnit.MILLISECONDS) 如果我們改成 asyncResult.get() 效果還是一樣的嗎?

肯定是不一樣的。

再說(shuō)一次:Dubbo 作為開(kāi)源的中間件,有可能會(huì)運(yùn)行在各種不同的 JDK 版本中,且該方法是它主鏈路上的核心代碼,對(duì)于特定的 JDK 版本來(lái)說(shuō),這個(gè)優(yōu)化確實(shí)是對(duì)于性能的提升有很大的幫助。

所以寫(xiě)中間件還是有點(diǎn)意思哈。

最后,再送你一個(gè)為 Dubbo 提交源碼的機(jī)會(huì)。

在其下面的這個(gè)類(lèi)中:

org.apache.dubbo.rpc.AsyncRpcResult

還是存在這兩個(gè)方法:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
但是上面的 get() 方法只有測(cè)試類(lèi)在調(diào)用了:

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
完全可以把它們?nèi)扛牡粽{(diào)用 get(long timeout, TimeUnit unit) 方法,然后把 get() 方法直接刪除了。

我覺(jué)得肯定是能被 merge 的。

如果你想為開(kāi)源項(xiàng)目做貢獻(xiàn),熟悉一下流程,那么這是一個(gè)不錯(cuò)的小機(jī)會(huì)。

被 merge 后你就可以去吹牛了,畢竟是為 Apache 頂級(jí)開(kāi)源項(xiàng)目貢獻(xiàn)過(guò)源碼的人,說(shuō)話(huà)音調(diào)都可以加高點(diǎn)。

看完JDK并發(fā)包源碼的這個(gè)性能問(wèn)題,我驚了!
好了,本文的技術(shù)部分就到這里啦。

下面這個(gè)環(huán)節(jié)叫做[荒腔走板],技術(shù)文章后面我偶爾會(huì)記錄、分享點(diǎn)生活相關(guān)的事情,和技術(shù)毫無(wú)關(guān)系。我知道看起來(lái)很突兀,但是我喜歡,因?yàn)檫@是一個(gè)普通博主的生活氣息。


本站聲明: 本文章由作者或相關(guān)機(jī)構(gòu)授權(quán)發(fā)布,目的在于傳遞更多信息,并不代表本站贊同其觀(guān)點(diǎn),本站亦不保證或承諾內(nèi)容真實(shí)性等。需要轉(zhuǎn)載請(qǐng)聯(lián)系該專(zhuān)欄作者,如若文章內(nèi)容侵犯您的權(quán)益,請(qǐng)及時(shí)聯(lián)系本站刪除。
換一批
延伸閱讀

9月2日消息,不造車(chē)的華為或?qū)⒋呱龈蟮莫?dú)角獸公司,隨著阿維塔和賽力斯的入局,華為引望愈發(fā)顯得引人矚目。

關(guān)鍵字: 阿維塔 塞力斯 華為

倫敦2024年8月29日 /美通社/ -- 英國(guó)汽車(chē)技術(shù)公司SODA.Auto推出其旗艦產(chǎn)品SODA V,這是全球首款涵蓋汽車(chē)工程師從創(chuàng)意到認(rèn)證的所有需求的工具,可用于創(chuàng)建軟件定義汽車(chē)。 SODA V工具的開(kāi)發(fā)耗時(shí)1.5...

關(guān)鍵字: 汽車(chē) 人工智能 智能驅(qū)動(dòng) BSP

北京2024年8月28日 /美通社/ -- 越來(lái)越多用戶(hù)希望企業(yè)業(yè)務(wù)能7×24不間斷運(yùn)行,同時(shí)企業(yè)卻面臨越來(lái)越多業(yè)務(wù)中斷的風(fēng)險(xiǎn),如企業(yè)系統(tǒng)復(fù)雜性的增加,頻繁的功能更新和發(fā)布等。如何確保業(yè)務(wù)連續(xù)性,提升韌性,成...

關(guān)鍵字: 亞馬遜 解密 控制平面 BSP

8月30日消息,據(jù)媒體報(bào)道,騰訊和網(wǎng)易近期正在縮減他們對(duì)日本游戲市場(chǎng)的投資。

關(guān)鍵字: 騰訊 編碼器 CPU

8月28日消息,今天上午,2024中國(guó)國(guó)際大數(shù)據(jù)產(chǎn)業(yè)博覽會(huì)開(kāi)幕式在貴陽(yáng)舉行,華為董事、質(zhì)量流程IT總裁陶景文發(fā)表了演講。

關(guān)鍵字: 華為 12nm EDA 半導(dǎo)體

8月28日消息,在2024中國(guó)國(guó)際大數(shù)據(jù)產(chǎn)業(yè)博覽會(huì)上,華為常務(wù)董事、華為云CEO張平安發(fā)表演講稱(chēng),數(shù)字世界的話(huà)語(yǔ)權(quán)最終是由生態(tài)的繁榮決定的。

關(guān)鍵字: 華為 12nm 手機(jī) 衛(wèi)星通信

要點(diǎn): 有效應(yīng)對(duì)環(huán)境變化,經(jīng)營(yíng)業(yè)績(jī)穩(wěn)中有升 落實(shí)提質(zhì)增效舉措,毛利潤(rùn)率延續(xù)升勢(shì) 戰(zhàn)略布局成效顯著,戰(zhàn)新業(yè)務(wù)引領(lǐng)增長(zhǎng) 以科技創(chuàng)新為引領(lǐng),提升企業(yè)核心競(jìng)爭(zhēng)力 堅(jiān)持高質(zhì)量發(fā)展策略,塑強(qiáng)核心競(jìng)爭(zhēng)優(yōu)勢(shì)...

關(guān)鍵字: 通信 BSP 電信運(yùn)營(yíng)商 數(shù)字經(jīng)濟(jì)

北京2024年8月27日 /美通社/ -- 8月21日,由中央廣播電視總臺(tái)與中國(guó)電影電視技術(shù)學(xué)會(huì)聯(lián)合牽頭組建的NVI技術(shù)創(chuàng)新聯(lián)盟在BIRTV2024超高清全產(chǎn)業(yè)鏈發(fā)展研討會(huì)上宣布正式成立。 活動(dòng)現(xiàn)場(chǎng) NVI技術(shù)創(chuàng)新聯(lián)...

關(guān)鍵字: VI 傳輸協(xié)議 音頻 BSP

北京2024年8月27日 /美通社/ -- 在8月23日舉辦的2024年長(zhǎng)三角生態(tài)綠色一體化發(fā)展示范區(qū)聯(lián)合招商會(huì)上,軟通動(dòng)力信息技術(shù)(集團(tuán))股份有限公司(以下簡(jiǎn)稱(chēng)"軟通動(dòng)力")與長(zhǎng)三角投資(上海)有限...

關(guān)鍵字: BSP 信息技術(shù)
關(guān)閉
關(guān)閉