《Effective java中文第2版》讀書筆記1

2條:遇到多個構造器參數時要考慮用構建器   

    某個類的屬性較多,初始化的時候又有一些是必須初始化的,而且類型有形同,  

    比如new Contact("姓名","顯示名","手機號","飛信號","所在地",年齡,性別);   

    前5個屬性是String 類型,後2個是int類型,在填寫構造方法的時候很容易填寫錯位,或者少填寫,或者顛倒了屬性,   

    如下方法可以減少這種錯誤發生的機率,   

  1. Contact contact = new Contact();     
  2.     contact.setName("姓名");     
  3.     contact.setDisplayName("顯示名");     
  4.     contact.setPhoneNumber("手機號");     
  5.     contact.setFetionNumber("飛信號");     
  6.     contact.setHometown("所在地");     
  7.     contact.setAge(23);     
  8.     contact.setGender(0);     

這麼寫是通常的做法,看起來還不夠清晰,我們在每個set方法裏retrun一個Contact類型,比如

  1. public Contact setName(String name)     
  2.    {     
  3.        this.name = name;     
  4.        return this;     
  5.    }    

這樣上面的構造Contact的代碼就可以這麼寫了

  1. Contact contact = new Contact() .setName("姓名")     
  2.                                     .setDisplayName("顯示名")     
  3.                                     .setPhoneNumber("手機號")     
  4.                                     .setFetionNumber("飛信號")     
  5.                                     .setHometown("所在地")     
  6.                                     .setAge(23)     
  7.                                     .setGender(0);    

 

    這樣寫是不是更清爽了!屬性不會再填寫錯誤了!而且閱讀代碼的時候也一目瞭然,都給Contact初始化了那些屬性,和屬性的值是什麼!   

3條:用私有構造器或者枚舉類型強化Singleton屬性   

 建議使用如下方法創建單例類   

  1. public final class Elvis     
  2.     {     
  3.         private static Elvis INSTANCE;     
  4.         private Elvis(){};     
  5.         synchronized public static Elvis getInstance()     
  6.         {     
  7.             if( INSTANCE == null )     
  8.             {     
  9.                 INSTANCE = new Elvis();     
  10.             }     
  11.             return INSTANCE;     
  12.         }     
  13.         //執行其他操作     
  14.         private Object readResolve()     
  15.         {     
  16.             return INSTANCE;     
  17.         }     
  18.     }    
    這種構建方法好處,組成類的成員聲明很清楚地表明瞭這個類是個Singleton,並且也解決了INSTANCE的同步問題,   

    沒有暴露共有的INSTANCE變量,這樣更有力於隱藏類的內部實現,   

    另外,改做法也很容易就可以修改成非單例模式,加上的readResolve方法可以保證反序列化時也是同一個對象。   

     

4條:通過私有構造器強化不可實例化的能力   

    我們軟件中常用的常量集(Constants),工具集(Tool,Utility)都應該是不可實例化的類,那麼他們應該如下構建   

  1. public final class Constants     
  2.     {     
  3.         private Constants()     
  4.         {     
  5.             throw new AssertionError();     
  6.         }     
  7.         //其他常量的定義,或者靜態方法的實現;     
  8.     }    

這樣可以防止被繼承,被實例化。   

       

5條:避免創建不必要的對象   

    創建一個String對象,最佳方式如下

  1. String str = "初始化值";     
  2.     如果一個String在創建的時候我們不確定他的值,建議如下創建     
  3.     String str = "";     
  4.     強烈反對     
  5.     String str = null;     
  6.     這種寫法,因爲會有NullPointerException這個異常的危險,另外主要還有潛在隱患,比如做了如下操作     
  7.     str += "ABC";     
  8.     那麼str = nullABC;了這個不是想要的結果。     
  9.     str = "";的初始化方式也有他的不足之處,在判斷str是否有效的時候就要多加一個長度的判斷如下     
  10.     if( str==null||str.length()<=0 ){}    

因爲str的長度初始爲0。  
      
    對於JDK1.5以後的版本有自動封裝,自動拆裝的功能,所以要儘量使用基本類型,尤其是長整型因爲long 和Long很容易看差,而影響效率。  
    總之,要吝嗇使用new操作符,他不僅會增加對象的數目,而且也給垃圾回收造成麻煩,還有潛在的內存泄漏風險,另外new操作也比較耗時。  
      
第13條:使類和成員的可訪問性最小化  
第14條:在共有類中使用訪問方法而非共有域  
    public的權限太大了,建議使用包級私有權限,也就是缺省(default)的訪問級別。這樣可以增加軟件的防禦性,public的變量應該杜絕使用,  
    可以使用get,set方法代替。這樣可以不隱蔽數據域,也方便以後修改數據域。  
      
第16條:複合優先於繼承  
第17條:要麼爲繼承而設計,並提供文檔說明,要麼就禁止繼承  
    繼承不便於擴展,耦合性很大,繼承打破了封裝,因爲基類向子類暴露了實現細節,基類的內部細節通常對子類是可見的,建議繼承只限定在包內使用,  
    否則是非常危險的,對軟件的防禦行也有很大的破壞作用。  
    當父類的實現改變時可能要相應的對子類做出改變,也不能在運行時改變由父類繼承來的實現。  

 

  

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章