激情久久久_欧美视频区_成人av免费_不卡视频一二三区_欧美精品在欧美一区二区少妇_欧美一区二区三区的

服務(wù)器之家:專注于服務(wù)器技術(shù)及軟件下載分享
分類導(dǎo)航

PHP教程|ASP.NET教程|JAVA教程|ASP教程|

服務(wù)器之家 - 編程語言 - JAVA教程 - 淺談Java多線程編程中Boolean常量的同步問題

淺談Java多線程編程中Boolean常量的同步問題

2020-01-12 14:27johnshen0708 JAVA教程

這篇文章主要介紹了淺談Java多線程編程中Boolean常量的同步問題,主要針對(duì)線程之間同步了不同的布爾對(duì)象的問題,需要的朋友可以參考下

在JAVA中通過synchronized語句可以實(shí)現(xiàn)多線程并發(fā)。使用同步代碼塊,JVM保證同一時(shí)間只有一個(gè)線程可以擁有某一對(duì)象的鎖。鎖機(jī)制實(shí)現(xiàn)了多個(gè)線程安全地對(duì)臨界資源進(jìn)行訪問。
 
同步代碼寫法如下:
 
代碼1:

?
1
2
3
4
5
Object obj = new Object();
...
synchronized(obj) {
 //TODO: 訪問臨界資源
}

JAVA的多線程總是充滿陷阱,如果我們用Boolean作為被同步的對(duì)象,可能會(huì)出現(xiàn)以下兩種情況:
 
一. 以為對(duì)一個(gè)對(duì)象加鎖,實(shí)際同步的是不同對(duì)象。
 
代碼2:
 

?
1
2
3
4
5
6
7
8
9
10
11
private volatile Boolean isTrue = false;
 
publich void aMethod() {
 ...
 synchronized(isTrue) {
  isTrue = !isTrue;
  //TODO: 訪問臨界資源
  isTrue = !isTrue;
 }
 ...
}

 咋一看上面的代碼沒有問題,由于使用了synchronized(isTrue)同一時(shí)間只能有一個(gè)線程訪問臨界資源,但事實(shí)并不是這樣。因?yàn)閒alse和true這兩個(gè)常量對(duì)應(yīng)著兩個(gè)不同的對(duì)象。當(dāng)isTrue產(chǎn)生變化時(shí),很可能導(dǎo)致不同的線程同步了不同的對(duì)象。JAVA的自動(dòng)裝箱會(huì)將false變?yōu)锽oolean.FALSE,將true變?yōu)锽oolean.TRUE(同時(shí)這也說明了此處若將false改為Boolean.FALSE其結(jié)果也是一樣的)。寫一個(gè)以上情況的測(cè)試代碼如下:
 
代碼3:
 

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
public class BooleanTest {
   
  private volatile Boolean isTrue = Boolean.FALSE; //此處用false也一樣
   
  public void aMethod() {
    for(int i=0;i<10;i++) {
      Thread t = new Thread() {
        public void run() {
          synchronized(isTrue) {
            isTrue = !isTrue;
            System.out.println(Thread.currentThread().getName() + " - isTrue=" + isTrue);
            try{
              Double ran = 1000 * Math.random();
              Thread.sleep(ran.intValue());
            }catch(InterruptedException e) {}
             
            if(!isTrue) System.out.println(Thread.currentThread().getName() + " - Oh, No!");
 
            isTrue = !isTrue;
          }
        }
      };
      t.start();
    }
  }
   
  public static void main(String... args) {
    BooleanTest bt = new BooleanTest();
    bt.aMethod();
  }
}

 運(yùn)行以上代碼,不時(shí)的會(huì)看到 " - Oh, No!",表示不同的線程同時(shí)進(jìn)入到synchronized代碼塊中。
 
二. 以為同步的是不同對(duì)象,實(shí)際是一個(gè)對(duì)象。
 
有時(shí)候我們可能希望在多個(gè)對(duì)象上進(jìn)行同步,如果使用了Boolean作為被同步對(duì)象,很可能會(huì)導(dǎo)致本來應(yīng)該沒有關(guān)系的兩個(gè)同步塊使用了相同對(duì)象的鎖。示例如下:
 
代碼4:
 

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
private volatile Boolean aBoolean = Boolean.FALSE;
 
private volatile Boolean anotherBoolean = false;
 
public void aMethod() {
 ...
 synchronized(aBoolean) {
  //TODO: 訪問臨界資源1
 }
 ...
}
 
public void anotherMethod() {
 ...
 synchronized(anotherBoolean) {
  //TODO: 訪問臨界資源2
 }
 ...
}

 假設(shè)原本aMethod和anotherMethod分別會(huì)被兩組沒有關(guān)系的線程調(diào)用。但是由于Boolean.FALSE和false指向的是同一個(gè)對(duì)象,可能導(dǎo)致對(duì)臨界資源2的訪問被臨界資源1阻塞了(反之亦然)。
 
以上兩種情況說明,在使用同步塊時(shí),盡量不用使用Boolean對(duì)象作為被同步對(duì)象,不然可能會(huì)出現(xiàn)意想不到的問題,或者對(duì)以后的代碼修改造成陷阱。
 
從此也可以看出,任何對(duì)常量的同步都是有風(fēng)險(xiǎn)的。如果一定要對(duì) Boolean 進(jìn)行同步,一定要用 new 操作符來創(chuàng)建 Boolean 對(duì)象。

延伸 · 閱讀

精彩推薦
主站蜘蛛池模板: www.91sese| 麻豆蜜桃在线观看 | 国产成年人在线观看 | 久久久青青草 | 精品国产一区二区三区四 | 91网址在线播放 | 国产一区二区三区手机在线 | 亚洲午夜久久久久 | 国产精品视频不卡 | 成人毛片100部 | 欧美日韩国产成人在线观看 | 久久精品一区二区三区不卡牛牛 | 91精品免费在线 | 免费看一级片 | 国产免费片 | 国产人成精品一区二区三 | 欧美激情性色生活片在线观看 | 黄网站在线观 | 国产精品av久久久久久网址 | 蜜桃麻豆视频 | 久草视频福利在线观看 | 国产精品久久999 | 精品在线观看一区 | 国产女厕一区二区三区在线视 | 亚洲视频在线观看免费 | 欧美一级高清片_欧美高清aa | 国产电影精品久久 | 一区二区三区视频播放 | 久久中文一区 | 免费黄色av | 久久精品无码一区二区三区 | 欧美成人性生活片 | 国产交换3p国产精品 | 国产精品美女久久久久久不卡 | 久久最新免费视频 | 99综合视频 | 亚洲电影免费观看国语版 | 成人情欲视频在线看免费 | 国产精品自拍啪啪 | 女人解衣喂奶电影 | 91中文在线观看 |