第七色在线视频,2021少妇久久久久久久久久,亚洲欧洲精品成人久久av18,亚洲国产精品特色大片观看完整版,孙宇晨将参加特朗普的晚宴

為了賬號(hào)安全,請(qǐng)及時(shí)綁定郵箱和手機(jī)立即綁定
已解決430363個(gè)問題,去搜搜看,總會(huì)有你想問的

Java volatile 重新排序預(yù)防范圍

Java volatile 重新排序預(yù)防范圍

慕田峪9158850 2021-06-22 17:14:07
對(duì) volatile 字段的寫入和讀取分別防止在 volatile 字段之前和之后重新排序讀/寫。寫入 volatile 變量之前的變量讀/寫不能重新排序在它之后發(fā)生,而從 volatile 變量讀取之后的讀/寫不能重新排序在它之前發(fā)生。但這項(xiàng)禁令的范圍是什么?據(jù)我了解, volatile 變量只能防止在使用它的塊內(nèi)重新排序,對(duì)嗎?為了清楚起見,讓我舉一個(gè)具體的例子。假設(shè)我們有這樣的代碼:int i,j,k;volatile int l;boolean flag = true;void someMethod() {    int i = 1;    if (flag) {        j = 2;    }    if (flag) {        k = 3;        l = 4;    }}顯然,write tol將阻止 write tok重新排序,但它會(huì)阻止重新排序?qū)懭雐和j關(guān)于l? 換句話說,可以寫入i并j在寫入之后發(fā)生l嗎?更新 1感謝大家花時(shí)間回答我的問題 - 我很感激。問題是你回答了錯(cuò)誤的問題。我的問題是關(guān)于范圍,而不是關(guān)于基本概念。問題基本上是編譯器在代碼中保證“發(fā)生在之前”與 volatile 字段的關(guān)系有多遠(yuǎn)。顯然編譯器可以保證在同一個(gè)代碼塊內(nèi),但是封閉塊和對(duì)等塊呢 - 這就是我的問題。@Stephen C 說,volatile 保證發(fā)生在整個(gè)方法主體內(nèi)部的行為之前,即使在封閉塊中,但我找不到任何確認(rèn)。他說得對(duì)嗎,有什么地方可以確認(rèn)嗎?讓我再舉一個(gè)關(guān)于范圍界定的具體例子來澄清事情:setVolatile() {   l = 5;} callTheSet() {   i = 6;   setVolatile();}i在這種情況下,編譯器會(huì)禁止重新排序?qū)懭雴幔炕蛘呔幾g器不能/沒有被編程來跟蹤在 volatile 情況下其他方法中發(fā)生的事情,并且i可以重新排序?qū)懭胫鞍l(fā)生setVolatile()?或者編譯器根本不重新排序方法調(diào)用?我的意思是在某處必須有一個(gè)點(diǎn),當(dāng)編譯器將無法跟蹤某些代碼是否應(yīng)該在某些 volatile 字段寫入之前發(fā)生時(shí)。否則,一個(gè)易失性字段寫入/讀取可能會(huì)影響一半程序的排序,如果不是更多的話。這是一種罕見的情況,但它是可能的。此外,看看這個(gè)報(bào)價(jià)在新的內(nèi)存模型下,volatile 變量不能相互重新排序仍然是正確的。不同之處在于現(xiàn)在不再那么容易對(duì)它們周圍的正常字段訪問重新排序?!霸谒麄兣赃叀?。這句話暗示,有一個(gè)范圍,其中 volatile 字段可以防止重新排序。
查看完整描述

3 回答

?
互換的青春

TA貢獻(xiàn)1797條經(jīng)驗(yàn) 獲得超6個(gè)贊

顯然,寫入 l 會(huì)阻止寫入 k 的重新排序,但它會(huì)阻止寫入 i 和 j 的重新排序嗎?

重新排序的含義并不完全清楚;看我上面的評(píng)論。

然而,在Java 5+內(nèi)存模型,我們可以說,寫入ij所發(fā)生之前,寫入l將是另一個(gè)線程可見后已經(jīng)閱讀l......只要沒有寫ij寫后l。

這確實(shí)會(huì)限制寫入i和的指令的任何重新排序j。具體來說,它們不能在寫入后的內(nèi)存寫入屏障之后移動(dòng)到l,因?yàn)檫@可能導(dǎo)致它們對(duì)第二個(gè)線程不可見。

但這項(xiàng)禁令的范圍是什么?

本身沒有禁令。

您需要了解指令、重新排序和內(nèi)存屏障只是實(shí)現(xiàn) Java 內(nèi)存模型的特定方式的細(xì)節(jié)。該模型實(shí)際上是根據(jù)保證在任何“格式良好的執(zhí)行”中可見的內(nèi)容來定義的。

據(jù)我了解, volatile 會(huì)阻止在使用它的塊內(nèi)重新排序,對(duì)嗎?

實(shí)際上,沒有。塊不考慮。重要的是方法中語句的(程序源代碼)順序。


@Stephen C 說,volatile 保證發(fā)生在整個(gè)方法主體內(nèi)部的行為之前,即使在封閉塊中,但我找不到任何確認(rèn)。

確認(rèn)是 JLS 17.4.3。它聲明如下:

在每個(gè)線程 t 執(zhí)行的所有線程間動(dòng)作中,t 的程序順序是一個(gè)總順序,它反映了根據(jù) t 的線程內(nèi)語義執(zhí)行這些動(dòng)作的順序。

如果所有動(dòng)作以與程序順序一致的總順序(執(zhí)行順序)發(fā)生,則一組動(dòng)作是順序一致的,此外,變量 v 的每次讀取 r 都會(huì)看到寫入 w 寫入 v 的值,使得:

  • w 在執(zhí)行順序中排在 r 之前,并且

  • 在執(zhí)行順序中,沒有其他寫入 w' 使得 w 在 w' 之前并且 w' 在 r 之前。

順序一致性是對(duì)程序執(zhí)行中的可見性和順序的非常有力的保證。在順序一致的執(zhí)行中,所有單獨(dú)的動(dòng)作(例如讀取和寫入)都有一個(gè)與程序順序一致的總順序,每個(gè)單獨(dú)的動(dòng)作都是原子的,對(duì)每個(gè)線程都是立即可見的。

如果一個(gè)程序沒有數(shù)據(jù)競(jìng)爭(zhēng),那么程序的所有執(zhí)行都將看起來是順序一致的。

請(qǐng)注意,此定義中沒有提及塊或范圍。


查看完整回答
反對(duì) 回復(fù) 2021-06-23
?
catspeake

TA貢獻(xiàn)1111條經(jīng)驗(yàn) 獲得超0個(gè)贊

我很想知道 volatile 變量如何影響其他字段

易失性變量確實(shí)會(huì)影響其他字段。如果 JIT 編譯器認(rèn)為重新排序不會(huì)對(duì)執(zhí)行輸出產(chǎn)生任何影響,則可以對(duì)指令重新排序。因此,如果您有 6 個(gè)獨(dú)立變量存儲(chǔ),則 JIT 可以重新排序指令。

但是,如果您將變量設(shè)為 volatile,即在您的情況下為變量l,那么 JIT 將不會(huì)在 volatile STORE 之后重新排序任何變量 STORES。我認(rèn)為這是有道理的,因?yàn)樵诙嗑€程程序中,如果我將變量l的值設(shè)為 4,那么我應(yīng)該將i設(shè)為 1,因?yàn)樵谖业某绦蛑校?strong>我是在l之前編寫的,最終是程序順序語義(如果我是沒有錯(cuò))。

Note that volatile variables does two things:
  1. 編譯器不會(huì)在易失性存儲(chǔ)之后重新排序任何存儲(chǔ)/在易失性讀取之前不會(huì)重新排序任何讀取。

  2. 刷新加載/存儲(chǔ)緩沖區(qū),以便所有處理器都可以看到更改。

編輯:

這里的好博客:http : //jpbempel.blogspot.com/2013/05/volatile-and-memory-barriers.html


查看完整回答
反對(duì) 回復(fù) 2021-06-23
  • 3 回答
  • 0 關(guān)注
  • 187 瀏覽

添加回答

舉報(bào)

0/150
提交
取消
微信客服

購課補(bǔ)貼
聯(lián)系客服咨詢優(yōu)惠詳情

幫助反饋 APP下載

慕課網(wǎng)APP
您的移動(dòng)學(xué)習(xí)伙伴

公眾號(hào)

掃描二維碼
關(guān)注慕課網(wǎng)微信公眾號(hào)