大话设计模式
前言
1.精彩的代码是如何想出来的,要比看到精彩的代码更加令人兴奋
2.如果想成为一名优秀的软件设计师,了解优秀软件设计的演变过程比学习优秀的设计本身更有价值,因为设计的演变过程中蕴含着大的智慧。
3.简略模式(strategy)
4.面向对象的优点-可维护-可扩展-可复用-灵活性好
5.面向对象的想法
6.继承和多态
封装变化点就是面向对象的一种很重要的思维
第一章:代码无错就是优
1.1.
面试时要考虑全面,用面向对象的思想编写程序。最好回答问题尺举个例子
1.2.
初学者都有代码的毛病,命名规范,代码复用,面向对象,
1.6
面向对象的好处:
分析编程思想,考虑通过封装继承多态把程序的耦合度降低,使用设计模式使用程序更加灵活,容易修改,并且易于复用。
1.8
所谓业务的封装就是把业务逻辑和界面逻辑分离开,让他们的耦合度下降,只有分离开,才可以达到容易维护或扩展(业务逻辑通俗说就是后台判断逻辑代码,界面逻辑就是界面的显示代码)
1.11
类图的表示法
》继承--动物-鸟-乌鸦:用空心三角形+实线
》接口--大雁-飞翔:用空心三角形+虚线
》关联--企鹅-气候:用实线+箭头(当两个类有关系的时候)
》聚合--大雁-雁群:用菱形+实线箭头(聚合表示一种弱的拥有关系,a对象可以包含b对象,但b对象不是a对象的一部分)
》合成--鸟-翅膀:用菱形(实)+实线箭头+两头有一个1和2(合成是一种强的拥有关系,体现了严格的部分和整体的关系,部分和整体的生命周期一样【DPE】)1和2是:基类:表明这个类有几个实例。
》依赖--动物-氧气:用虚线箭头
1.简单工长模型的使用范围:
也就是说:到底要实例化谁,将来会不会增加实例化的对象,这些很容易变化的地方,应该考虑用一个单独的类来做这个创建实例化的过程这就是简单工厂模型
1.2.
面对对象的类并不是类越多越好,类的划分是为了封装,但分类的基础是抽象,具有相同属性和功能的抽象集合才是类
2.
策略模式
它定义了算法家族,分别封转起来,让他们之间可以相互替换,此模式让算法的变化,不会影响到使用算法的客户。
2.1.
2.2.
策略模式是一种定义一系列算法的方法,从概念上来看,所有这些算法完成的都是相同的工作,只是实现不同,它可以以相同的方式调用所有的算法,减少了各种算法类与使用算法类之间的耦合(DPE)。
2.3
策略模式的优点
.1策略模式的策略类(Strategy)层次为上下文类(Context)定义了一系列的可供重用的算法或行为。继承有助于吸取出算法的公共功能(DP),
.2策略模式是简化了单元测试,因为每个算法都有自己的类,可以通过自己的接口单独测试(DPE)。
2.4
有时我们不得不在客户端的代码中使用switch条件语句,因为当不同的行为堆砌在一个类中时,就很难避免使用条件语句来选择合适的行为,将这些行为封装在一个个独立的Strategy类中,可以在使用这些行为的类中消除条件语句(DP)。
2.5
策略模式的使用范围
策略模式就是用来封装算法的但在实践中,我们发现可以用它来封装几乎任何类型的规则,要在分析过程中听到需要在不同时间应用部同的业务规则,就可以考虑使用策略模式处理这种变化的可能性(DPE)。
2.7
任何需求的变更都是需要成本的
3.1
单一职责原则
单一职责原则:就是对一个类而言应该仅有一个引起它变化的原因。
3.2
分析:
如果一个类承担的职责过多,就等于把这些职责耦合在一起,一个职责的变化可能会削弱或者抑制这个类完成其他职责的能力,这种耦合会导致脆弱的设计,当变化发生时,设计会遭到意想不到的破坏(ASD)。
3.3
>1软件设计真正要做的许多内容,就是发现职责并把这些职责相互分离(ASD),要判断是否应该分离出类来,那就是如果你能够想到多余一个的动机去改变一个类,那么这个类就具有多于一个的职责(ASD),就应该考虑类的职责分离。例如:游戏页面和逻辑,将它们分离有利于页面的改动。
>2我们编程时,要在类的职责分离上多做思考,做的单一职责,这样你的代码才是真正的易维护,易扩展,易复用,灵活多样
4.1
开发-封闭原则
开发-封闭原则是面向对象设计的核心所在,遵循这个原则可以带来面向对象技术所声称的巨大好处,也就是可维护,课扩展,可复用,灵活性好,开发人员应该对程序中呈现出频繁变化的那部分作出抽象,然而,对于应用程序中的每个部分都刻意的进行抽象同样不是一个好主意,拒绝不成熟的抽象和抽象本身一样重要。
4.2
特点:
.1对于扩展是开放的
.2对于更改是封闭的
在出现变化时,我们就创建抽象来隔离以后发生的同类变化
对于程序的改动是通过增加新的代码进行的,而不是更改现有的代码[ASD],
5.1
依赖倒置原则
抽象不应该依赖细节,细节应该依赖于抽象,其实就是底层模块谁也不依赖谁
要针对接口编程,不要对实现编程.
5.3
依赖倒置其实就是可以说是面向对象设计的标志,用那种语言编写程序不重要,如果编写是考虑的都是如何针对抽象编程而不是针对细节编程,即程序中所有的依赖关系都是终止于抽象类或者接口,那就是面向对象的设计,反之那就是过程化的设计[ASD].
5.2
里氏替换原则:
子类型必须能够替换他们的父类型(ASD)
而子类可以也能够在父类的基础上增加新的行为
6.1
装饰模式:
动态的给一个对象添加一些额外的职责,就增加功能来说,装饰模式比生成子类更加灵活.
6.2
模式类图:
6.3
装饰模式是利用setComponent(添加组装饰方法)来对对象进行包装的,这样每个装饰对象的实现就和如何使用这个对象分离开了,每个装饰对象值关心自己的功能,不需要关心如何被添加的对象链当中(DPE)
6.4
装饰模式总结
装饰模式是为已有功能动态的添加更多的功能的一种方式,
当系统需要新功能的时候,是向旧的类中添加新的代码,这些新的代码通常修饰了原有类的核心职责或主要行为.新加入的东西主要是为了满足一些只在某种特定情况下才会执行的特殊行为,因此,当需要执行特殊行为时,客户代码就可以再运行时根据需要有选择的,俺顺序的使用装饰功能包装对象了.
6.5
有效的把类的核心职责和装饰功能区分开了,而且可以去除相关类中重重复的装饰逻辑
7.1
代理模式:
为其他对象提供一种代理易控制对这个对象的访问(DP).
7.2:
代理模式类图:
8.1
工厂模式:
定义一个用于创建对象的接口,让子类决定实例化哪一个类,工厂方法使一个类的实例化延迟到其子类。
8.2
工厂模式类图:
三:命令模式
命令模式:将一个请求封装为一个对象,从而使你可用不同的请求对客户进行参数化;对请求排队或记录请求日志,以及支持可撤销的操作。
1.原型模式;
2.怎么样,大鸟,这样一来,客户端的代码就清爽的很多了,而且你要是想改某份简历,只要对这份简历做一定的修改就可以了,不会影响到其他的简历,相同的部分就不用在重复了,不过不知道这样子对性能是不是有大的提高呢?
3.“当然是大大提高,你想呀,每NEW一次,都需要执行一次构造函数,如果构造函数的执行时间很长,那么多次的执行这个初始化操作就实在太低了,一般在初始化的信息不发烧变化的情况下,克隆是最好的办法,这既隐藏了对象创建的细节,又对性能是大大的提高,何乐而不为呢?”
4.“的确,我开始也没感觉到它的好处,听你这么一说,感觉这样做的好处还真不少,它等于是不用重新初始化对象,而是动态地获取对象运行的状态,这个模式真的很不错。”
9.5:
浅复制和深复制“别高兴的太早,如果我现在要改动需求,你就有头痛了。你在简历里的数据都是string的,也就是值类型,MemberwiseClone()方法是这样的,如果字段是值类型的,则对该字段执行逐位复制,如果字段是引用类型,而复制引用但不复制引用对象,因此原始对象及其复本引用同一对象,什么意思呢,就是说如果你的简历类当中有对象引用,那么引用的额对象数据时不会克隆过来的。”“没听太懂,为什么不能一同复制过来呢?”“举个例子你就明白了,你现在的简历类当中有一个’设置工作经历的方法,在现实设计中,一般会在有一个‘工作经历’类当中有‘时间区间’和‘公司名称’等属性,‘简历’类直接调用这个对象即可,你按照我说的在写写看看,”好的我试试。“半个小时后,小菜的第三个版本。代码结构图工作记忆类,一次设置因为三个引用都指向了同一个对象,你写的和说的都很好,就是这个原因,这叫做‘浅复制’。被复制对象的所有变量都含有所有的变量都含有雨原来的对象相同的值,而所有的对其他对象的引用都依然指向原来的对象,但我们可能更需要,这样的一种需求,把要复制的对象所引用的对象都复制一遍。比如刚才的例子,我们希望abc三个引用的对象的变量指向复制过的新对象,而不是原有的被引用的对象。”“那如果‘简历’引用了‘工作经历’,'‘工作经历’在引用‘公司’,‘公司’咋引用‘职位’.....不同的,复制时就一变二,二变三,此时,我们就叫这种方式为‘深复制’,深复制把引用对象的变量指向复制过的新对象,而不是原有的被引用的对象。”“那如果‘简历’对象引用了‘工作经历,’工作经历‘在引用‘公司’,‘公司’在引用‘职位’,。。这样一个引用一个,很多层,如何办?”那如果;简历