隨筆-204  評論-149  文章-0  trackbacks-0

          http://www.javaeye.com/topic/109150

          http://itchaser.javaeye.com/blog/440335

          http://www.javaeye.com/topic/11315


          還得了解一下Java內(nèi)存模型。。。

          看了一下Java虛擬機規(guī)范,就比較清楚了

          posted on 2009-06-28 00:50 Frank_Fang 閱讀(1158) 評論(5)  編輯  收藏 所屬分類: Java編程

          評論:
          # re: Java volatile關(guān)鍵字語義 2009-07-01 21:45 | Frank_Fang

          package test.thread.two;



          /**
           * 你會發(fā)現(xiàn)next( )和getValue( )都是synchronized。如果你只對其中一個做synchronized,那么另一個就被忽略了,于是其它線程就能肆無忌憚地調(diào)用它了。
           * 一定要記住:所有訪問共享資源的方法都必須是synchronized的,否則程序肯定會出錯。
           * 而invariant( )倒不是synchronized的,這是因為它是供測試線程用的,因此我們希望它能隨時被調(diào)用,只有這樣才能算是真正的測試。
           *
           
          */


          public class SynchronizedEvenGenerator implements Invariant {
              
              
          //不管加不加volatile都會發(fā)生沖突,只有將getValue()前加上synchronized才不會發(fā)生沖突
               private  volatile int i;

              
          public synchronized void next() {
                  i
          ++;
                  i
          ++;
              }


              
          //假如這個方法的synchronized去掉了,發(fā)生沖突是必然的
              
          //你可能聽說過,為了提高性能,在讀或?qū)懺訑?shù)據(jù)的時候,你應(yīng)該避免使用同步。
              //這個建議是非常危險而錯誤的

              public synchronized int getValue() {
                  
          return i;
              }


              
          // Not synchronized so it can run at
              
          // any time and thus be a genuine test:
              public InvariantState invariant() {
                  
          int val = getValue();
                  
          if (val % 2 == 0)
                      
          return new InvariantOK();
                  
          else
                      
          return new InvariantFailure(new Integer(val));
              }


              
          public static void main(String[] args) {
                  SynchronizedEvenGenerator gen 
          = new SynchronizedEvenGenerator();
                  
          new InvariantWatcher(gen, 4000); // 4-second timeout
                  while (true)
                      gen.next();
              }

          }

          原子操作

          "原子操作(atomic operation)是不需要synchronized",這是Java多線程編程的老生常談了。所謂原子操作是指不會被線程調(diào)度機制打斷的操作;這種操作一旦開始,就一直運行倒結(jié)束,中間不會有任何context switch(切換到另一個線程)。

          通常所說的原子操作包括對非longdouble型的primitive進行賦值,以及返回這兩者之外的primitive。之所以要把它們排除在外是因為它們都比較大,而JVM的設(shè)計規(guī)范又沒有要求讀操作和賦值操作必須是原子操作(JVM可以試著去這么作,但并不保證)。不過如果你在longdouble前面加了volatile,那么它就肯定是原子操作了。

          如果你一知半解地把這條規(guī)則用到SynchronizedEvenGenerator.java上,就會發(fā)覺:

          public synchronized int getValue() { return i; }

          好像很符合原子操作的定義嘛。但是把synchronized去掉試試看,程序很快就出了錯。這是因為,雖然return i是原子操作,但刪掉synchronized之后,別的線程就能在它還處于不穩(wěn)定狀態(tài)的時候讀到它了。在做這種優(yōu)化之前,先得真正弄懂這么做的后果是什么。這里沒有現(xiàn)成的經(jīng)驗。

            回復(fù)  更多評論
            
          # re: Java 內(nèi)存模型及 volatile關(guān)鍵字語義 2009-07-21 01:56 | tt
          @Frank_Fang

          這段代碼在哪里?如何才可以運行測試

          我在另外一個網(wǎng)站上看到的不是如此  回復(fù)  更多評論
            
          # re: Java 內(nèi)存模型及 volatile關(guān)鍵字語義 2009-07-21 01:57 | tt
          http://hi.baidu.com/lifa868/blog/item/22bc7718926ad772dbb4bd0e.html

          這里講的,即時非long及double也未必一會是原子的。。。
          還有代碼中說://不管加不加volatile都會發(fā)生沖突,只有將getValue()前加上synchronized才不會發(fā)生沖突

          會這樣么?  回復(fù)  更多評論
            
          # re: Java 內(nèi)存模型及 volatile關(guān)鍵字語義 2009-07-24 10:55 | Frank_Fang
          volatile保證了線程間變量的可見性,但是不保證能夠進行互斥訪問
          synchronized保證對變量的互斥訪問,當(dāng)進入或者退出synchronized代碼塊時會對將線程中的此本地變量副本(這個要區(qū)別TSD)寫到主存中,這也確保不同線程間對此變量的修改可見性
            回復(fù)  更多評論
            
          # re: Java 內(nèi)存模型及 volatile關(guān)鍵字語義 2009-09-04 10:59 | gee
          @Frank_Fang
          樓上正解  回復(fù)  更多評論
            
          主站蜘蛛池模板: 芮城县| 邵东县| 大石桥市| 凌云县| 安陆市| 稷山县| 临桂县| 元朗区| 临汾市| 伊金霍洛旗| 旌德县| 东平县| 罗山县| 东源县| 谢通门县| 扎兰屯市| 监利县| 迁安市| 白银市| 兰坪| 安国市| 两当县| 新龙县| 泗洪县| 微博| 从化市| 富阳市| 綦江县| 绩溪县| 麻江县| 孙吴县| 黄龙县| 界首市| 蕉岭县| 曲松县| 张家川| 余姚市| 调兵山市| 和龙市| 汨罗市| 新郑市|