好久没有更新博客了,一个自己这段时间忙于项目;另外一个原因就是自己这段时间干了一件美满的事情,找到了人生的另一半(虽然现在还是女朋友阶段);但是我还是希望能够有足够的时间、心情能够将自己这段时间的一些收获用文字的形式记录下来;
说到设计模式,其实大家都不陌生,应该说都是非常熟悉的。因为在项目里面都会不知不觉的用到它们,我想最耳熟能详的单例模式,大家应该都是熟悉的“不要不要”的吧。但是如果我问你,在设计模式里面有6条最基本的设计原则,你知道是哪些吗?
单一职责原则,这条原则大家望文生义就应该知道它大概的主旨思想了。讲的是一个对象类、方式里面尽量只完成一件事情,只完成属于它所在范畴里面的事情。比如:吃饭这件事情,你会需要做什么事情呢?吃饭之前你肯定需要先洗菜、切菜、炒菜、煮饭...,那如果我们用程序来模拟一下这个场景呢?首先我们来定义一个菜类Vegetables,在这个菜类里面我们希望做什么事情呢?首先定义两个属性,分别表示整个做菜过程中的时间和菜的数量,然后有三个方法分别表示洗菜、切菜、煮菜的动作。请看下面的类图:,然后我们再来看看饭的动作,它应该具有哪些属性呢?首先我们同样需要定义一个属性time,两个方法:淘米、设时开煮,请看下面的类图:。看到这里你会不会觉得有什么不妥的地方吗?这里我们留个自由发挥的地方,大家可以自己想想。
里氏替换原则,这什么意思呢?光从字面理解好像并不能很准确理解它的含义。让我们来看看,最正宗的定义:如果对每一个类型为S的对象o1,都有类型为T的对象o2,使得以T定义的所有程序P在所有的对象o1都代换成o2时,程序P的行为没有发生变化,那么类型S是类型T的子类型。哦,其实里氏替换原则说白了就是面向对象里面的抽象、继承。通过抽象、继承的扩展我们可以获得很好的扩展性、封装性。下面让我们来模拟一下这个常用场景:我们去买水果,通过水果的颜色、大小、价格来决定是否购买。买完水果回家,我们需要洗洗、尝尝水果。首先我们肯定需要模拟出一个基类,里面应该包含水果的相关属性。然后通过扩展该基类来获取不同水果,最后就开始进入洗、吃的阶段了。请看下面的类图:,通过里氏替换原则,我们将可以很容易的扩展出新的水果。
依赖倒置原则,这个名字可能比较抽象。但是如果写出下面几个特性:1.模块之间的依赖关系都是通过接口或者抽象类发生的,两个模块之间不存在直接的依赖关系;2.接口或者抽象类不依赖于实现类;3.实现类依赖于接口或者抽象类;通过上面的特性分析,我们就能够总结出依赖倒置原则的好处了:能够有效的降低系统之间的耦合,增强系统的稳定性;说到这里也许你就应该明白,依赖倒置说白了就是面向抽象编程。当我们在一个对象里面需要注入另外一个对象的时候,通常来说有两种方式:1.构造函数注入;2.Set方法注入;3.接口注入;让我们来具体看一个例子:,如果我拿到了C照是不是不管宝马还是奔驰我都应该可以开呢?那肯定是的,所以我们让宝马和奔驰都实现ICar接口,然后通过构造函数注入的方式去让每一个司机都有一辆车。这样的话,我们最终只要在device方法里面调用ICar的run方法就可以了。以后不管司机是否会换车,我们只要添加新的ICar实现就好了。
接口隔离原则,说白了就是面向接口变成。但是这个原则要求我们做到:接口尽量简单、纯洁,就是一个接口里面不要去做太多的事情;
迪米特原则,就是封装原则。这个原则在我们的项目开发过程中可能经常会遇到,比如我们需要给第三公司提供SDK,但是我又想第三方公司对我们公司的SDK尽量少知道,只需要按照我给他们的手册一步一步调用指定的方法就可以了,其他的不需要他们关心;所以当我们在项目里面想要按照迪米特原则去写代码的时候,就是一个类只和自己有关系的那个类发生关系,其他的我遵循高内聚、低耦合;请看下面的例子:老师让学习委员清点班级女生的人数。UML图如下:在这三个类里面,老师只需要知道学习委员,通过学习委员来清点人数。当学习委员点数的时候,响应的女生只需要回答:“到”就可以了。
开闭原则,相信这个原则大家肯定非常的熟悉。”面向扩展开放、面向修改关闭“,其实在上面的依赖倒置原则和里氏替换原则我们就可以在一定程度上面能够实现扩展开放,然后迪米特原则我们又可以在一定程度上面实现修改关闭,这样的话就要求我们在定义一个类的时候,尽量遵照最小权限原则;