设计模式
其实,很多东西都是经历过,遇到问题,解决了,然后才知道。大学时候学过设计模式,但是没有实践过,很快就忘了。后来开发的时候遇到一些问题,解决了,然后感觉像哪个设计模式,回过头去看设计模式,感觉挺有用的。
学完设计模式以后,建议用简单、高效、易维护的态度去设计开发。
(1) 什么是设计模式
软件设计模式(Design pattern),又称设计模式,是一套被反复使用、多数人知晓的、经过分类编目的、代码设计经验的总结。 使用设计模式是为了可重用代码、让代码更容易被他人理解、保证代码可靠性、程序的重用性。
(2) 设计模式的分类
创建型模式:对象实例化的模式,创建型模式用于解耦对象的实例化过程。
结构型模式:把类或对象结合在一起形成一个更大的结构。
行为型模式:类和对象如何交互,及划分责任和算法。
(3) 各个模式的关键点
单例模式:某个类只能有一个实例,提供一个全局的访问点。
工厂模式:定义一个创建对象的接口,让子类决定实例化那个类。
抽象工厂模式:创建相关或依赖对象的家族,而无需明确指定具体类。
建造者模式:封装一个复杂对象的构建过程,并可以按步骤构造。
原型模式:通过复制现有的实例来创建新的实例。
适配器模式:将一个类的方法接口转换成客户希望的另外一个接口。
组合模式:将对象组合成树形结构以表示“”部分-整体“”的层次结构。
装饰模式:动态的给对象添加新的功能。
代理模式:为其他对象提供一个代理以便控制这个对象的访问。
亨元模式:通过共享技术来有效的支持大量细粒度的对象。
外观模式:对外提供一个统一的方法,来访问子系统中的一群接口。
桥接模式:将抽象部分和它的实现部分分离,使它们都可以独立的变化。
模板模式:定义一个算法结构,而将一些步骤延迟到子类实现。
解释器模式:给定一个语言,定义它的文法的一种表示,并定义一个解释器。
策略模式:定义一系列算法,把他们封装起来,并且使它们可以相互替换。
状态模式:允许一个对象在其对象内部状态改变时改变它的行为。
观察者模式:对象间的一对多的依赖关系。
备忘录模式:在不破坏封装的前提下,保持对象的内部状态。
中介者模式:用一个中介对象来封装一系列的对象交互。
命令模式:将命令请求封装为一个对象,使得可以用不同的请求来进行参数化。
访问者模式:在不改变数据结构的前提下,增加作用于一组对象元素的新功能。
责任链模式:将请求的发送者和接收者解耦,使的多个对象都有处理这个请求的机会。
迭代器模式:一种遍历访问聚合对象中各个元素的方法,不暴露该对象的内部结构。
设计模式的六大原则
- 开闭原则(Open Close Principle)
- 里氏代换原则(Liskov Substitution Principle)
- 依赖倒转原则(Dependence Inversion Principle)
- 接口隔离原则(Interface Segregation Principle)
- 迪米特法则,又称最少知道原则(Demeter Principle)
- 合成复用原则(Composite Reuse Principle)
(4) 概说23种设计模式
(4.1) 单例模式 (Singleton Pattern)
(4.1.1) 什么是单例模式
单例模式是为确保一个类只有一个实例,并为整个系统提供一个全局访问点的一种模式方法。
(4.1.2) 单例模式的特点
优点:
1、在内存里只有一个实例,减少了内存的开销,尤其是频繁的创建和销毁实例。
2、避免对资源的多重占用(比如写文件操作)。
缺点:
没有接口,不能继承,与单一职责原则冲突,一个类应该只关心内部逻辑,而不关心外面怎么样来实例化。
(4.1.3) 单例模式的应用
1、要求生产唯一序列号。
2、WEB 中的计数器,不用每次刷新都在数据库里加一次,用单例先缓存起来。
3、创建的一个对象需要消耗的资源过多,比如 I/O 与数据库的连接等。 例如: 在计算机系统中,线程池、缓存、日志对象、对话框、打印机、显卡的驱动程序对象常被设计成单例。
(4.1.4) 单例模式的实现
单例模式的实现有很多种。以下是比较常用的几种。
(4.1.4.1) 饿汉式单例
饿汉式单例是指在方法调用前,实例就已经创建好了。
(4.1.4.2) 懒汉式单例
(4.1.4.3) 双检锁/双重校验锁(DCL,即 double-checked locking)
(4.2) 工厂模式 (Factory Pattern)
(4.2.1) 什么是工厂模式
工厂模式
工厂模式就好比房屋中介,你想租房,通过中介去租不同的房子。
(4.2.2) 工厂模式的特点
优点:
1、一个调用者想创建一个对象,只要知道其名称就可以了。
2、扩展性高,如果想增加一个产品,只要扩展一个工厂类就可以。
3、屏蔽产品的具体实现,调用者只关心产品的接口。
缺点:
每次增加一个产品时,都需要增加一个具体类和对象实现工厂,使得系统中类的个数成倍增加,在一定程度上增加了系统的复杂度,同时也增加了系统具体类的依赖。这并不是什么好事。
(4.2.3) 工厂模式的应用
1、日志记录器:记录可能记录到本地硬盘、系统事件、远程服务器等,用户可以选择记录日志到什么地方。
2、数据库访问,当用户不知道最后系统采用哪一类数据库,以及数据库可能有变化时。
3、设计一个连接服务器的框架,需要三个协议,”POP3”、”IMAP”、”HTTP”,可以把这三个作为产品类,共同实现一个接口。
(4.2.4) 实现
(4.3) 抽象工厂模式
(4.3.1) 什么是抽象工厂模式
抽象工厂模式(Abstract Factory Pattern)是围绕一个超级工厂创建其他工厂。该超级工厂又称为其他工厂的工厂。
抽象工厂模式好比所有中介的中介,就行房屋中介、婚姻中介、买菜中介的中介管家一样,租房找中介管家,中介管家找房屋中介,然后租房。
(4.3.2) 抽象工厂模式的特点
特点
(4.3.3) 抽象工厂模式的应用
- QQ 换皮肤,一整套一起换。
- 生成不同操作系统的程序。
(4.3.4) 抽象工厂模式的实现
(4.4) 建造者模式 (Builder Pattern)
注意事项:与工厂模式的区别是:建造者模式更加关注与零件装配的顺序。
(4.4.1) 什么是建造者模式
指将一个复杂对象的构造与它的表示分离,使同样的构建过程可以创建不同的表示,这样的设计模式被称为建造者模式。
计算机是由 CPU、主板、内存、硬盘、显卡、机箱、显示器、键盘、鼠标等部件组装而成的,采购员不可能自己去组装计算机,而是将计算机的配置要求告诉计算机销售公司,计算机销售公司安排技术人员去组装计算机,然后再交给要买计算机的采购员。
游戏中的不同角色,其性别、个性、能力、脸型、体型、服装、发型等特性都有所差异。
汽车中的方向盘、发动机、车架、轮胎等部件也多种多样。
每封电子邮件的发件人、收件人、主题、内容、附件等内容也各不相同。
(4.4.2) 建造者模式的特点
优点:
1、建造者独立,易扩展。
2、便于控制细节风险。
缺点:
1、产品必须有共同点,范围有限制。
2、如内部变化复杂,会有很多的建造类。
(4.4.3) 建造者模式的应用
一些基本部件不会变,而其组合经常变化的时候。
1、计算机是由 CPU、主板、内存、硬盘、显卡、机箱、显示器、键盘、鼠标等部件组装而成的,购买电脑时选取自己喜欢的CPU、主板、内存条、硬盘、显卡、机箱、显示器、键盘、鼠标等部件。
2、JAVA 中的 StringBuilder,可以拼接不同的对象。
(4.4.4) 建造者模式的实现
References
[1] 23种设计模式
[2] 23种设计模式全面解析
[3] 24种设计模式及案例