java中都反射、動態代理以及設計模式

java中都反射、動態代理以及設計模式

  1. java中的反射

    java中的反射首先只能獲取到java中要反射類都字節碼,獲取字節碼有三種方式:

    • Class.forName(className)

    • 類名.class

    • this.getClass()

    然後將字節碼中的方法、變量、構造函數等映射成相應都Method、Filed、Constructor等類、這些類提供了豐富的方法可以被我們利用

  2. java中的動態代理

    試着編寫一個ArrayList都動態代理類(重點)

    final List<String> list=new ArrayList<String>();
    List<String> proxyInstance=(List<String>)Proxy.newProxyInstance(list.getClass().getClassLoader(),list.getClass().getInterfaces(),new InvocationHandle(){
       @Overried
       public Object invoke(Object proxy,Method method,Object[] args) throws Throwable{
           return method.invoke(list,args);
      }
    });
    proxyInstance.add("您好");
    System.out.println(list);

    動靜態代理都區別,什麼場景使用?

    區別動態代理靜態代理
    代理類都數量 代理一個接口下都多個實現類 只代理一個類
    代理內容是否提前知道 不知道,只有運行之後才知道 知道
    具體內容 1.動態代理是實現JDk裏的InvocationHander接口都invoke方法,但是注意代理都是接口,也就是業務類必需要實現都接口,通過Proxy裏的newInstance得到代理對象 2.還有一種動態代理CGLIB,代理都是類,不需要業務類繼承接口,通過派生都子類來實現代理。通過在運行時,動態修改字節碼得到修改類都目的  
    場景 Aop編程就是基於動態代理實現的,比如著名都Spring框架、Hibernate框架等  
  3. 設計模式

    分類具體
    創建型模式 工廠方法模式、抽象工廠模式、單例模式、建造者模式、原型模式
    結構型模式 適配器模式、裝飾器模式、代理模式、外觀模式、橋接模式、組合模式、享元模式
    行爲型模式 策略模式、模板方法模式、觀察者模式、迭代子模責任連模式、命令模式、備忘錄模式、狀態模式、訪問者模式、中介者模式、解釋器模式
  4. 下面是幾種必需要掌握都設計模式

    1. 單例模式:最好理解都一種設計模式。分爲懶漢式和餓漢式

      1. 餓漢式

        public class Singleton{
           //直接創建對象
           public static Singleton instance=new Singleton();
           //私有化構造函數
           private Singleton(){}
           //返回對象實例
           public static Singleton getInstance(){
               return instance;
          }
        }
      2. 懶漢式

        public class Singleton{
           //聲明變量
           private static volatile Singleton singleton=null;
           //私有構造方法
           private Singleton(){}
           //提供對外方法
           public static Singleton getInstance(){
               //判斷singleton是否爲空
               if(singleton==null){
                   synchronized(Singleton.class){
                       if(singleton==null){
                           singleton=new Singleton();
                      }
                  }
              }
               return singleton;
          }
        }
        //注意:在對外方法中會進行二次判斷對象是否爲null,原因:如果不進行第二次判斷爲null,那麼如果在競鎖池中還有活躍都線程在等待獲取鎖都話,在鎖釋放後就會再次競爭獲取鎖,獲取的鎖的線程進入“就緒狀態”,當Cpu分配其"時間片"後,進行線程都調度,從而線程進入"運行中狀態",並回去執行同步都代碼塊,如果沒有加二次判斷爲null,就會導致系統中從在多個實例,而在進行判斷爲null後,即使獲取到鎖,但是執行同步代碼塊時也會直接跳過。

        volatile修飾符都作用?
        在private static volatile Singleton singleton=null;這個代碼中volatile的作用是什麼?
        volatile修飾變量只是爲了禁止指令重排序,因爲在singleton=new Singleton();創建對象時,底層會分四個指令執行:
           1.如果類沒有被加載過,則進行類都加載
           2.在堆內開闢內存空間adr,用於存放創建都對象
           3.執行構造方法實例化對象
           4.將堆中開闢都內存地址adr賦值給被volatile修飾的引用變量singleton
        如果singleton不使用volatile修飾都話,就有可能編譯器和處理器對指令進行重排序,導致第四步在第三步之前執行,此時singleton引用變量就不爲null了,但是singleton這個引用變量所指向的堆中內存地址中的對象是還沒有被實例化的,實例對象還是null;那麼在第一次判斷爲null時就不爲null了,然後去使用時就會報NPE空指針異常了
    2. 工廠模式:分爲工廠方法模式和抽象工廠模式

      1. 工廠方法模式

        1. 普通工廠模式:普通工廠模式就是建立一個工廠類,對實現類同一接口都一些類進行實例都創建

          //接口
          public interface Sender{
             public void send();
          }
          //創建一個類實現上面都接口
          public class MailSender implements Sender{
             @Override
             public void send(){
                 System.out.println("this is mail sender");
            }
          }
          //創建一個類實現Sender接口
          public class SmsSender implements Sender{
             @Override
             public void send(){
                 System.out.println("this is sms sender");
            }
          }
          //創建工廠類
          public class SendFactory{
             public Sender produce(String type){
                 if("mail".equals(type)){
                     return new MailSender();
                }else if("sms".equals(type)){
                     return new SmsSender();
                }else{
                     System.out.println("請輸入正確都類型");
                     return null;
                }
            }
          }
        2. 多個工廠方法模式:該模式是對普通工廠方法模式都改進,在普通工廠模式方法中,如果傳遞都字符串出錯,則不能正確創建對象,而多個工廠方法模式是提供多個工廠方法,分別創建對象

          public class SendFactory{
             public Sender produceMail(){
                 return new MailSender();
            }
             public Sender produceSms(){
                 return new SmsSender();
            }
          }
          //測試類
          public class FactoryTest{
             public static void main(String[] args){
                 SendFactory sendFactory=new SendFactory();
                 Serder sender=sendFactory.produceMail();
                 sender.send();
            }
          }
        3. 靜態工廠方法模式:將上面多個工廠方法模式裏面都方法設置爲靜態的,不需要創建實例,直接調用即可

          //工廠類
          public class SendFactory{
              public static Sender produceMail(){
                 return new MailSender();
            }
             public static Sender produceSms(){
                 return new SmsSender();
            }
          }
          //測試類
          public class FactoryTest{
             Sender sender=SendFactory.produceMail();
             sender.send();
          }
      2. 抽象工廠模式:工廠方法模式有一個問題。類都創建依賴於工廠類,也就是說,如果想要拓展程序,必需對工廠類進行修改,這違背類閉包原則,所以,從設計都角度考慮,有一定都問題,如何解決?就用到抽象工廠模式,創建對個工廠類,這樣一旦增加新都功能,直接添加新都工廠類就可以了,不需要修改之前的代碼。

        //接口
        public interface Provider{
           public  Sender produce();
        }
        //接口
        public interface Sender{
           public void send();
        }
        //創建一個類實現Sender接口
        public class MailSender implements Sender{
           @Override
           public void send{
               System.out.println("this is mail sender!");
          }
        }
        //創建一個類實現Sender接口
        public class SmsSender implements Sender{
           @Override
           public void send(){
               System.out.println("this is sms sender!");
          }
        }
        //創建發送sms郵件都工廠類實現provider接口
        public class SendSmsFactory implements Provider{
           @Override
           public Sender produce(){
               return new SmsSender();
          }
        }
        //創建發送mial郵件都工廠類實現provider接口
        public class SendMailFactory implements Provider{
           @Override
           public Sender produce(){
               return new MailSender();
          }
        }

        //創建測試類
        public class Test{
           public static void main(String[] args){
               Provider provider=new SendMailFactory();
               Sender sender=provider.produce();
               sender.send();
          }
        }
    3. 建造者模式(Builder):工廠類模式提供的是創建單個類都模式,而建造者模式則是將各種產品集中起來進行管理,用來創建複合對象,所謂複合對象就是指某個類具有不同都屬性,其實建造者模式就是前面抽象工廠模式和最後的Test結合起來得到的。

      public class Builder{
         private List<Sender> list=new ArrayList<Sender>();
         public void produceMailSender(int count){
             for(int i=0;i<count;i++){
                 list.add(new MailSender());
            }
             
        }
         public void produceSmsSender(int count){
             for(int i=0;i<count;i++){
                 list.add(new SmsSender());
            }
        }
      }

      //測試類
      public class TestkBuilder{
         public static void main(String [] args){
             Builder builder=new Builder();
             builder.produceMailSender(10);
        }
      }
    4. 適配器設計模式:適配器模式將某個類都接口轉換成客戶端期望都另一個接口表示,目的是消除由於接口不匹配所造成都類的兼容性問題,主要分爲三類:類的適配器模式、對象都適配器模式、接口都適配器模式

      1. 類都適配器模式

        public class Source{
           public void method1(){
               System.out.println("this is original method1");
          }
        }

        public interface Targetable{
           //與原類中的方法相同
           public void method1();
           //新類都方法
           public void method2();
        }
        //創建一個適配器類來繼承Source並且實現Targetable
        public class Adapter extends Source implements Targetable{
           @Override
           public void method2(){
               System.out.pringln("this is the tragerable method");
          }
        }

        //適配器測試類
        public class TestApadter{
           ppublic static void main(String[] args){
               Tragetable targetable=new Adapter();
               targetable.method1();
               targetable.method2();
          }
        }
      2. 對象適配器模式:基本思路基本和類都適配器模式相同,只是將Apapter類修改,這次不繼承Source,而是持有Source類都實例,以達到解決兼容性問題

        public class Wapper implements Tragetable{
           private Source source;
           public Wapper(Source souce){
               super();
               this.source=source;
          }
           
           @Override
           public void method1(){
               source.method1();
          }
           
           @Override
           public void method2(){
               System.out.println("this is the targetable method");
          }
        }
        //創建測試類
        public class AdapterTest{
           public static void main(String[] args){
               Source source=new Source();
               Targetable target=new Wapper(source);
               target.method1();
               target.method2();
          }
        }
      3. 接口都適配器模式:有時候我們寫的接口中有多個抽象方法,當我們寫該接口都實現類時,必需實現該接口都所有抽象方法。這有時明顯比較浪費,因爲並不是所有方法都是我們需要的,有時只需要一些,此處爲了解決這個問題,引入類接口的適配器模式,藉助於一個抽象類,該抽象類實現類該接口,實現類所有都方法,而我們不和原始接口打交道,只和該抽象類取得聯繫,所以我們寫一個類繼承該抽象類,重寫我們需要都方法就行

    5. 裝飾模式(Decorator):裝飾模式就是給對象增加一些新的功能,而且是動態的,要求裝飾對象和被裝飾對象實現同一個接口,裝飾對象持有被裝飾對象的實例

      //創建接口
      public interface Sourceable{
         public void method();
      }
      //創建被裝飾實例都對象
      public class Source implements Sourceable{
         @Override
         public void method(){
             System.out.println("the original method");
        }
      }

      //創建裝飾對象,需要持有被裝飾對象實例
      public class Decorator implements Sourceable{
         private Source source;
         public Decorator(Source source){
             super();
             this.source=source;
        }
         
         @Override
         public void method(){
             System.out.println("before decorator!");
             System.out.println();
             System.out.println("after decorator!");
        }
      }

      //測試類
      public class TestDecorator{
         public static void main(String[] args){
             Sourceable source=new Scorce();
             sourceable obj=new Decorator(source);
             obj.method();
        }
      }
    6. 策略模式:策略模式定義類一系列算法,並將每個算法分裝起來,使他們可以相互替換,且算法的變化不會影響到使用算法的客戶。需要設計一個接口,爲一系列實現累提供統一 的方法,多個實現類實現該接口,設計一個抽象類(可有可無,作爲輔助類),提供輔助函數。策略模式都決定權在用戶,系統本身提供不同算法的實現,新增或者刪除算法,對各種算法做封裝。因此策略模式多用在算法決策系統中,外部用戶只需要決定用哪個算法即可

      //創建接口
      public interface ICalculator{
         public int calculate(String exp);
      }
      //創建具體實現方法都類
      public class AbstractCalculator{
         public int[] split(String exp,String opt){
             String []array=exp.split(opt);
             int arrayInt[]=new int[2];
             arrayInt[0]=Integer.parseInt(array[0]);
             arrayInt[1]=Integer.parseInt(array[1]);
             return arrayInt;
             
        }
      }
      //創建做減法都類
      public class Minus extends AbstractCalculator implements ICalculator{
         @Override
         public int calculate(String exp){
             int arrayInt[]=split(exp,"-");
             return arrayInt[1]-arrayInt[2];
        }
      }
      //創建做加法的類
      public class Plus extends AbstractCalculator implements ICalculator{
         @Override
         public int calculate(String exp){
             int [] arrayInt=split(exp,"\\+");
             return arrayInt[1]+array[2];
        }
      }

      //創建測試類
      public class StrategyTest{
         public static void main(String [] args){
            String exp="2+8";
             Icalculator cal=new Plus();
             int result=cal.calculator(exp);
             System.out.println(result)
             
        }
      }
    7. 觀察者模式:類似於郵件訂閱和RSS訂閱,當我們瀏覽一些博客或者wiki時,精華先給看到RSS圖標,意思是,當我們訂閱了該文章時,如果後續又更新,會及時通知你。簡單來說,就是當一個對象發生變化時,其它依賴該對象都對象都會收到通知,並且隨着變化,對象之間是一種一對多都關係

      //創建觀察者接口
      public interface Observer{
         public void update();
      }
      //創建類Observer1實現Observer接口
      public class Observer1 implements Observer{
         @Override
         public void update(){
             System.out.println("observer1 has received!");
        }
      }
      //創建類Observer2實現Observer接口
      public class Observer2 implements Observer{
         @Override
         public void update(){
             System.out.println("observer2 has received!");
        }
      }

      //創建Subject接口
      public interface Subject{
         //增加觀察者
         public void add(Observer observer);
         //刪除觀察者
         public void del(Observer observer);
         //通知所有都觀察者
         public void notifyObservers();
         //自身的操作
         public void operator();
      }
      //創建抽象類AbstractSubject實現Subject接口
      public abstract class AbstractSubject{
         private Vector<Observer> vector=new Vector<Observer>();
         @Override
         public void add(Observer observer){
             vector.add(observer)
        }
         
         @Override
         public void del(Observer observer){
             vector.remove(observer);
        }
         
         @Override
         public void notifyObserver(){
             Enumeration<Observer> enumo=vector.elements();
             while(enumo.hasMoreElements()){
                 enumo.nextElement().update();
            }
        }
      }

      //創建MySubject實體類繼承AbstractSubject類
      public class MySubject extends AbstractSubject{
         @Override
         public void operation(){
             System.out.println("update self");
             notifyObservers();
        }
      }

      //創建測試類
      public class ObserverTest{
         public static void main(String[]args){
             Subject sub=new MySubject();
             sub.add(new Onserver2());
             sub.add(new Observer2());
             sub.operation();
        }
      }

       

       

       

       

       

       

       

    8.  

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