设计模式学习(一)_六大原则

[TOC]

设计模式简介

设计模式是一套被反复使用的、多数人知晓的、经过分类编目的、代码设计经验的总结。使用设计模式是为了重用代码、让代码更容易被他人理解、保证代码可靠性。 毫无疑问,设计模式于己于他人于系统都是多赢的,设计模式使代码编制真正工程化,设计模式是软件工程的基石,如同大厦的一块块砖石一样。项目中合理地运用设计模式可以完美地解决很多问题,每种模式在现实中都有相应的原理来与之对应,每种模式都描述了一个在我们周围不断重复发生的问题,以及该问题的核心解决方案,这也是设计模式能被广泛应用的原因。

设计模式主要是基于以下面向对象设计原则

  • 对接口编程而不是对实现编程
  • 优先使用对象组合而不是继承

设计模式的六大原则

考软考的时候强行背下来,但是理解不深刻,索性还是自己整理学习一遍.23种设计模式则是遵循了这六大原则,达到了高内聚,低耦合,使程序可维护,可复用,可拓展

总原则、开闭原则(Open Close Principle)

开闭原则的意思是:对扩展开放,对修改关闭

[尽量不要更改源代码,而是在原有的基础上增加新的类—用抽象实现框架,用实现扩展细节]

1
2
3
4
5
6
例:
版本更新:尽量不更改源代码,可以增加新功能

员工迟到问题:可以制定迟到的晚下班,迟到多久就得加班多久等制度

即:上班总时长封闭,对于迟到一点开放

在程序需要进行拓展的时候,不能去修改原有的代码,实现一个热插拔的效果。简言之,是为了使程序的扩展性好,易于维护和升级。开闭原则具有理想主义色彩,想要达到这样的效果,我们需要使用接口和抽象类,在学习和理解设计模式的时候,则会更好更深刻的体会到这几个原则。

(菜鸟教程里把这一条替换了单一职责原则,而菜鸟付紫琴还Google了一下为什么菜鸟教程里面没有写单一职责原则….于是强行加进来,强行理解一下)

以下六条原则则是开闭原则的实现方法

1、单一职责原则(Single responsibility principle)

又称单一功能原则,一个类应该只有一个发生变化的原因.每一个职责都是变化的一个轴线,如果一个类有一个以上的职责,这些职责就耦合在了一起。这会导致脆弱的设计。当一个职责发生变化时,可能会影响其它的职责。另外,多个职责耦合在一起,会影响[复用性.例如:要实现逻辑和界面的分离。[高内聚,低耦合]

2、里氏代换原则(Liskov Substitution Principle)

里氏代换原则是面向对象设计的基本原则之一。 里氏代换原则中说,任何基类可以出现的地方,子类一定可以出现.

1
2
3
4
5
6
7
我的理解:

- 扩展功能(例如update)时继承父类,尽量不要覆盖重写,
- 重载父类的方法时,前置条件(即形参)要比父类的输入参数更宽松.
- 实现抽象方法时,方法的后置条件(即返回值)要更严格.

否则会使原有功能发生故障

设计模式中比较通用的做法是:原来的父类和子类都继承一个更通俗的基类,原有的继承关系去掉,采用依赖、聚合,组合等关系代替.

LSP 是继承复用的基石,只有当派生类可以替换掉基类,且软件单位的功能不受到影响时,基类才能真正被复用,而派生类也能够在基类的基础上增加新的特有的行为。里氏代换原则是对开闭原则的补充。实现开闭原则的关键步骤就是抽象化,而基类与子类的继承关系就是抽象化的具体实现,所以里氏代换原则是对实现抽象化的具体步骤的规范。

3、依赖倒转原则(Dependence Inversion Principle)

高层模块不应该依赖低层模块,二者都应该依赖其抽象;抽象不应该依赖细节;细节应该依赖抽象。

这个原则是开闭原则的基础,具体内容:面向接口编程,依赖于抽象而不依赖于具体。

1
2
3
4
例如:
类A直接依赖类B,假如要将类A改为依赖类C,则必须通过修改类A的代码来达成。这种场景下,类A一般是高层模块,负责复杂的业务逻辑;类B和类C是低层模块,负责基本的原子操作;假如修改类A,会给程序带来不必要的风险。

解决方案:将类A修改为依赖接口I,类B和类C各自实现接口I,类A通过接口I间接与类B或者类C发生联系,则会大大降低修改类A的几率。

4、接口隔离原则(Interface Segregation Principle)

这个原则的意思是:类依赖于最小接口,否则实现了不需要的方法,耦合度也增高.使用多个隔离的接口,比使用单个接口要好

1
2
3
4
5
例如:
客户端不应该依赖它不需要的接口;一个类对另一个类的依赖应该建立在最小的接口上。
问题由来:类A通过接口I依赖类B,类C通过接口I依赖类D,如果接口I对于类A和类B来说不是最小接口,则类B和类D必须去实现他们不需要的方法。

解决方案:将臃肿的接口I拆分为独立的几个接口,类A和类C分别与他们需要的接口建立依赖关系。也就是采用接口隔离原则。

它还有另外一个意思是:降低类之间的耦合度。由此可见,其实设计模式就是从大型软件架构出发、便于升级和维护的软件设计思想,它强调降低依赖,降低耦合。

5、迪米特法则,又称最少知道原则(Demeter Principle)

最少知道原则是指:一个实体应当尽量少地与其他实体之间发生相互作用,使得系统功能模块相对独立。一个类对他所依赖的类知道的越少越好

[今天用到activeMQ时,突然理解了这个法则的应用场景,屁颠屁颠的来更新这篇笔记]
[这种知识突然连成一片儿的感觉超级nice啊哈哈哈]

1
2
3
4
5
6
7
8
由于狭义迪米特法则要求两个类不必直接通信时,进行的方法调用应当由第三个类来转发调用.这样在系统中制造出大量的小方法,从而使系统显得凌乱.
其可以使局部的模块得到简化,但是也会造成模块间的通信效率降低,使模块间不容易协调.

但是迪米特法则讨论的是对象之间信息的流量,方向以及信息影响的控制.主要的意图是控制信息过载.要求一个模块应当尽可能的将自己的内部数据和实现细节隐藏起来,也就是要求有良好的封装性.

另以今天理解JMS和activeMQ为例,JMS是消息服务的一组规范和接口,activeMQ则是JMS的实现.
服务层和web层交互,模块间的依赖则存在一系列耦合关系.耦合越多,后期的维护工作则越难.改善模块间的调用关系.则应用到了消息中介,模块与模块之间互相不认识.消息的发送者和接收者互不影响,实现过程都被封装了.
即回到六字箴言--"高内聚,低耦合".

设计模式的门面模式(Facade) 和中介模式(Mediator),都是迪米特法则的应用.

啊哈,这两个模式还没有学习到,安排上了~

迪米特法则还有一个更简单的定义:只与直接的朋友通信。首先来解释一下什么是直接的朋友:每个对象都会与其他对象有耦合关系,只要两个对象之间有耦合关系,我们就说这两个对象之间是朋友关系。耦合的方式很多,依赖、关联、组合、聚合等。其中,我们称出现成员变量、方法参数、方法返回值中的类为直接的朋友,而出现在局部变量中的类则不是直接的朋友。也就是说,陌生的类最好不要作为局部变量的形式出现在类的内部。

6、合成复用原则(Composite Reuse Principle)

合成复用原则是指:尽量使用合成/聚合的方式,而不是使用继承。

设计模式的类型

根据设计模式的参考书 Design Patterns - Elements of Reusable Object-Oriented Software(中文译名:设计模式 - 可复用的面向对象软件元素) 中所提到的,总共有 23 种设计模式。

这些模式可以分为三大类:创建型模式(Creational Patterns)、结构型模式(Structural Patterns)、行为型模式(Behavioral Patterns)。

当然,我们还会讨论另一类设计模式:J2EE 设计模式。

序号 模式 & 描述 包括
1 创建型模式
这些设计模式提供了一种在创建对象的同时隐藏创建逻辑的方式,而不是使用 new 运算符直接实例化对象。这使得程序在判断针对某个给定实例需要创建哪些对象时更加灵活。
工厂模式(Factory Pattern)
抽象工厂模式(Abstract Factory Pattern)
单例模式(Singleton Pattern)
建造者模式(Builder Pattern)
原型模式(Prototype Pattern)
2 结构型模式
这些设计模式关注类和对象的组合。继承的概念被用来组合接口和定义组合对象获得新功能的方式。
适配器模式(Adapter Pattern)
过滤器模式(Filter、Criteria Pattern)
装饰器模式(Decorator Pattern)
外观模式(Facade Pattern)
享元模式(Flyweight Pattern)
代理模式(Proxy Pattern)
3 行为型模式
这些设计模式特别关注对象之间的通信。
责任链模式(Chain of Responsibility Pattern)
命令模式(Command Pattern)
解释器模式(Interpreter Pattern)
迭代器模式(Iterator Pattern)
中介者模式(Mediator Pattern)
备忘录模式(Memento Pattern)
观察者模式(Observer Pattern)
状态模式(State Pattern)
空对象模式(Null Object Pattern)
策略模式(Strategy Pattern)
模板模式(Template Pattern)
访问者模式(Visitor Pattern)
4 J2EE 模式
这些设计模式特别关注表示层。这些模式是由 Sun Java Center 鉴定的。
MVC 模式(MVC Pattern)
业务代表模式(Business Delegate Pattern)
组合实体模式(Composite Entity Pattern)
数据访问对象模式(Data Access Object Pattern)
前端控制器模式(Front Controller Pattern)
拦截过滤器模式(Intercepting Filter Pattern)服务定位器模式(Service Locator Pattern)
传输对象模式(Transfer Object Pattern)

设计模式之间的关系

菜鸟教程_设计模式之间的关系