1. 程式人生 > >菜雞的Java筆記 第二十九 單例設計模式

菜雞的Java筆記 第二十九 單例設計模式

SingleCase 單例設計模式
        1.單例設計模式的特點
        2.多例設計模式的特點
    內容
    單例設計模式
        現在如果說有這麼一個程式類

    class Singleton{
        private SingleCase(){} // 構造方法私有
        public void print(){
            System.out.println(
"***************"); } } // 這個時候程式類給出肯動是直接例項化物件,而後呼叫方法 public class SingleCase{ public static void main(String args[]){ Singleton inst = null;// 宣告物件 inst = new SingleCase(); // 例項化物件 inst.print(); } }

           
        在此時的 Singleton 類中一定存在有無參的構造方法,因為自動成的。
        但是構造方法雖然一般都會使用 public 宣告,可是也可以使用 private 宣告
        當構造方法使用 private 宣告之後 程式執行就會出錯
        因為此時構造方法被私有化了,所以我無法從外部進行構造方法的呼叫
        那麼現在在保證構造方法與 print() 方法都不做任何修改的前提下,要求通過一些適當的 Singleton 變化讓類外部可以得到 Singleton 類的例項化物件,並且呼叫 print() 方法
        於是有了以下的分析:
        分析一:現在程式的關鍵是在於構造方法上使用了 private (private SingleCase(){} // 構造方法私有了),那麼對於 private 的特點是隻能夠在本類中進行訪問
        那麼現在換一個思路:能不能說在本類準備好一個例項化物件呢?

    class Singleton{
        Singleton instance = new Singleton
        private SingleCase(){} // 構造方法私有
        public void print(){
            System.out.println("***************");
        }
    }
    // 這個時候程式類給出肯動是直接例項化物件,而後呼叫方法
    public class SingleCase{
        public static void main(String args[]){
            Singleton inst 
= null;// 宣告物件 } }


        分析二:此時內部宣告的 instance 屬性屬於一個普通屬性,那麼普通屬性有一個前提:在例項化物件後才可以呼叫,但是現在外部無法例項化物件
        那麼就考慮使用 static ,因為 static 不受到例項化物件的控制

    class Singleton{
        static Singleton instance = new Singleton
        private SingleCase(){} // 構造方法私有
        public void print(){
            System.out.println("***************");
        }
    }
    // 這個時候程式類給出肯動是直接例項化物件,而後呼叫方法
    public class SingleCase{
        public static void main(String args[]){
            Singleton inst = null;// 宣告物件
            inst = Singleton.instance;
            inst.print();
        }
    }


        分析三:強調過只要是類中的屬性都是應該進行 private 封裝,所以以上程式碼中 instance 屬性也應該進行封裝
        那麼一旦封裝了,就必須通過方法訪問,按照此時要訪問的是 static 屬性,並且類無法直接在外部產生例項化物件,那麼就編寫一個 static 方法

    class Singleton{
        private static Singleton instance = new Singleton();
        private SingleCase(){} // 構造方法私有
        public static Singleton getlnstance(){
            return instance;
        }
        public void print(){
            System.out.println("***************");
        }
    }
    // 這個時候程式類給出肯動是直接例項化物件,而後呼叫方法
    public class SingleCase{
        public static void main(String args[]){
            Singleton inst = null;// 宣告物件
            inst = Singleton.getlnstance();
            inst.print();
        }
    }

           
        分析四:這麼寫程式碼折騰一圈最終目的還是在外部使用例項化物件呼叫方法,那麼這種脫褲子放屁的意義在哪裡?
            所以這個時候通過記憶體關係可以發現,不管外部有多少個物件的宣告,最終所能產生的例項化物件只有一個
            也就是說本程式限制了例項化物件的產生,只維持了一個
            之所以將構造方法私有就是切斷了那麼自然無法產生新的例項化物件
            
        分析五:缺陷
        為了保證整個程式碼在操作的過程之中只會存在有唯一的一個例項化物件,並且不可更改,則可以利用 final 宣告
        面試題: 請編寫一個 Singleton 程式,並說明程式的主要特點    
            

    class Singleton{
        private static final Singleton INSTNCE = new Singleton();
        private SingleCase(){} // 構造方法私有
        public static Singleton getlnstance(){
    // instance = new Singleton();  這種程式碼的可能性還是有得 為了不讓其出現 加上 final
            return INSTNCE;
        }
        public void print(){
            System.out.println("***************");
        }
    }
    // 這個時候程式類給出肯動是直接例項化物件,而後呼叫方法
    public class SingleCase{
        public static void main(String args[]){
            Singleton inst = null;// 宣告物件
            inst = Singleton.getlnstance();
            inst.print();
        }
    }

           
        構造方法私有化,外部無法產生新的例項化物件,只能夠通過類提供的 static 方法取得唯一的一個物件的引用
        對於單例設計模式有兩類:餓漢式(以上的程式碼),懶漢式
            餓漢式:不管程式中是否有物件需要使用此類,那麼此類的物件都例項化好;
            懶漢式:在第一次使用的時候才進行例項化
        範例:觀察懶漢式

    class Singleton{
        private static Singleton instance;
        private SingleCase(){} // 構造方法私有了
        public static Singleton getlnstance(){
            if(instance == null){
                instance = new Singleton(); // 需要的時候進行例項化
            }
            return instance;
        }
        public void print(){
            System.out.println("***************");
        }
    }
    // 這個時候程式類給出肯動是直接例項化物件,而後呼叫方法
    public class SingleCase{
        public static void main(String args[]){
            Singleton inst = null;// 宣告物件
            inst = Singleton.getlnstance();
            inst.print();
        }
    }

           
            這兩個分類只是一個小小的概念,關鍵 還是將之前的單例設計模式編寫熟練
                
    多例設計模式
        不管是單例設計還是多例設計,本質就一個:構造方法私有化,內部產生例項化物件,只不過單例設計只產生一個,多例設計不產生多個
        例如:現在要求描述一週時間數的類,只能夠有七個物件
        例如:要求描述性別的類,只能有兩個
        範例:性別的描述

    class Sex{
        public static final int MALE_CH = 1;
        public static final int FEMALE_CH = 1;
        private static final Sex MALE = NEW Sex("男");
        private static final Sex FEMALE = NEW Sex("女");
        private String title;
        private Sex(String title){
            this.title;
        }
        public static Sex getlnstance(int ch){
            switch(ch){
                case MALE_CH:
                    return MALE;
                case FEMALE_CH:
                    return FEMALE;
                dafault:
                    return null;
            }
        }
        public String toString(){
            return this.title;
        }
    }
    public class SingleCase{
        public static void main(String args[]){
            Sex sex = Sex.getlnstance(Sex.MALE_CH);
            System.out.println(sex);
        }
    }

           
            多例只是單例的一種衍生品,本質上沒有區別
            
    總結
        1.對於單例設計模式,多例設計模式更希望理解它設計的出發點:限制物件產生
        2.程式的基本結構必須要記下