設計模式小總結
阿新 • • 發佈:2018-12-10
-
- 設計模式源於生活,是經驗的總結,用於解決一些具有代表性的問題。
- 設計模式的經典之處,就在於,解決了編寫程式碼的人和呼叫程式碼的人雙方的痛處。
- 開發原則
- ①單一職責
- ②里氏替換:採用里氏替換原則的目的就是增強程式的健壯性,版本升級時也可以保持非常好的相容性。即使增加子類,原有的子類還可以繼續執行。在實際專案中,每個子類對應不同的業務含義,使用父類作為引數,傳遞不同的子類完成不同的業務邏輯,非常完美!
- ③依賴反轉:依賴介面,不要依賴實現。
- ④介面隔離:要求在介面中儘量少公佈public方法,介面是對外的承諾,承諾越少對系統的開發越有利,變更的風險也就越少。
- ⑤迪米特原則:儘量不要對外公佈太多的public方法和非靜態的public變數,儘量內斂,多使用private、package-private、protected等訪問許可權。
- ⑥開閉原則:對擴充套件開放,對修改關閉。
- JDK中的設計模式
- 工廠模式
- 使用者不關係細節,只關心結果。
- 特徵:
- 簡單的工廠模式:可以將其理解成為一個建立物件的工具類。
- 工廠方法模式:使用者選擇工廠。
- 抽象工廠模式:使用者使用抽象工廠,不需要知道具體工廠。
- 框架中的應用:
- BeanFactory
- SqlSessionFactory
- DataSourceFactory
- 單例模式
- 特徵:資源共享,重複利用
- 問題:
- 併發訪問的安全問題-synchronized volatile
- 序列化與反序列化出現多例-readResolve()方法
- 私有靜態內部類持有實現延遲載入
- 併發測試安全性
- 解決方案:
- 餓漢式
- 懶漢式
- 註冊登記式
- 列舉式
- 框架中的應用
- Listener單例
- IOC容器單例
- 執行緒池單例
- 工廠單例
- Spring框架通過註冊登記的方式實現單例
- 原型模式
- 舉例:專案中使用DTO、VO,DTO和VO之間存在一些相同的屬性,從資料庫表中查詢出來的物件賦值給DTO,然後把DTO中的值再賦值給VO,最終VO中的值傳輸到View去。BeanUtils.copyProperties()工具類可以通過反射實現這個過程。
- 解決方案:
- 比較BeanUtils.copyProperties()的兩種實現
- 重寫clone()方法進行深度克隆(序列化方式)
public Object clone(){ try{ //save the object to a byte array ByteArrayOutputStream bout = new ByteArrayOutputStream(); ObjectOutputStream out = new ObjectOutputStream(bout); out.writeObject(this); out.close(); //read a clone of the object from byte array ByteArrayInputStream bin = new ByteArrayInputStream(bout.toByteArray()); ObjectInputStream in = new ObjectInputStream(bin); Object ret = in.readObject(); in.close(); return ret; }catch(Exception e){ return null; } }
- 代理模式
- 應用:AOP、攔截器
- 生活中:中介、黃牛、媒婆
- 解決方案:
- 靜態代理-人工干預
- 動態代理-動態實現
- JDK實現動態代理
- CGlib實現動態代理
- 動態代理的底層實現
- 原理:
- ①動態生成.java檔案
- ②Java檔案輸出到磁碟
- ③把生成的.java檔案編譯成.class檔案
- ④把編譯生成的.class檔案載入到JVM中
- ⑤返回位元組碼充足以後的新的代理物件
- https://blog.csdn.net/lxlmycsdnfree/article/details/71404121
- 原理:
- 實現程式碼:
- JDK動態代理
public class Meipo implements InvocationHandler{ Person target; public Object getInstance(){ this.target = person; Classs clazz = person.getClass(); return Proxy.newProsyInstance(clazz.getClassLoader,clazz.getInterfaces(),this); } @Overried public Object invoke(Object proxy, Method method, Obejct[] args){ System.out.println("before invoke"); method.invoke(this.target,args); System.out.pringln("after invoke"); return null; } }
- JDK動態代理
- 專案應用
- Spring專案AspectJ的應用
- SpringBoot專案spring-boot-starter-aop的應用
- 策略模式
- 應用:比較器、支付方式、固定演算法、計算器。
- 場景:根據使用者的需求處理資料的時候需要對演算法做出選擇,固定的一些演算法。
- 不同的策略都是實現了同一個介面,然後再重寫介面中的方法。
- 框架中的應用:Comparator
- 模板模式
- 使用:一個抽象類公開定義了執行它的方法的方式/模板。它的子類可以按需要重寫方法實現,但呼叫將以抽象類中定義的方式進行。
- JDK中的應用
讓子類可以重寫方法的一部分,而不是整個重寫,你可以控制子類需要重寫那些操作。
java.util.Collections#sort()
java.io.InputStream#skip()
java.io.InputStream#read()
java.util.AbstractList#indexOf() - 應用:JdbcTemplate
- 委派模式
- 實現程式碼
- DispatcherServlet 負責將請求委派給 Spring MVC 中其他的元件處理,比如注有 @Controller 或 @RestController 的 Controller類,Handler Mappers(處理器對映),View Resolvers(檢視解析器) 等等。
- 介面卡模式
- SpringMVC中的介面卡模式
- Spring定義了一個適配介面,使得每一種Controller有一種對應的介面卡實現類, 讓介面卡代替controller執行相應的方法。這樣在擴充套件Controller 時,只需要增加一個介面卡類就完成了SpringMVC的擴充套件了。
- SpringMVC中的介面卡模式
- 裝飾器模式
- IO流
- 框架中的應用:
- Servlet API中提供了一個request物件的Decorator設計模式的預設實現類HttpServletRequestWrapper,HttpServletRequestWrapper類增強了request物件的功能。
- IO流
- 觀察者模式
- https://blog.csdn.net/zhangxiaomin1992/article/details/55511396
例如在金融服務中,放款成功後,需要傳送站內信、傳送簡訊、傳送郵件通知使用者,可以使用觀察者實現。
- https://blog.csdn.net/zhangxiaomin1992/article/details/55511396