设计模
文章平均质量分 59
面向对象思考
这个作者很懒,什么都没留下…
展开
-
Aha!设计模式(1)-引言
投票结果 在上一个连载结束的时候,关于接下来的连载,作者曾经设想了几个题目。作者一度认为:Python应该最受大家的欢迎,所以事先做了一些准备,比如买书。 但是同时又存在另一种声音:设计模式也很重要。因为无论是作者本人还是身边的同事朋友,很多人都会经常会遇到设计模式。 犹豫再三,一直没有决定选择哪一个。最后接受了某人的建议,在公众号进行了一次投票。 以下是...原创 2018-10-29 21:02:32 · 426 阅读 · 0 评论 -
Aha!设计模式(3)-抽象工厂(2)
动机 《设计模式》引言中对于动机的说明如下: 用以说明一个设计问题以及如何用模式中的类、对象来解决该问题的特定情景。该情景会帮助你理解随后对模式更抽象的描述。 简单地说:就是设计模式的应用实例。 回到抽象工厂模式的动机。 考虑一个支持多种视感(look-and-feel)标准的用户界面工具包,例如 Motif和Presentation Manager。不同的...原创 2018-10-31 20:38:08 · 332 阅读 · 0 评论 -
Aha!设计模式(2)-抽象工厂(1)
《设计模式》的前两章分别介绍设计模式的概要和一个应用实例。对于一个设计模式的初学者来讲,应该不大好理解。 我们直接进入具体的设计模式。本文从抽象工厂模式说起。 名称 在面向对象的世界里,名称具有很重要的含义。名称一旦明确了,职责和行为差不多也就定了;反之如果没有办法为一个类,方法命名,往往就是职责和行为不清晰。 认真考虑名称 具体到今天的题目抽象工厂,稍加扩...原创 2018-10-30 21:06:04 · 328 阅读 · 0 评论 -
Aha!设计模式(5)-抽象工厂(4)
结构下图为抽象工厂模式的类图。 这个类图和前面出现过的类图唯一的区别就是使用了更加抽象的类名。所以就不在重复说明了。 这里说说另一个话题:画类图。抽象工厂模式的类图可以按照以下步骤(当然不是绝对的)画出: 首先可以个画出三个工厂类。 为每个工厂类添加两个产生产品的操作/方法。 画出两个产品系列的继承结构。 添加客户类。 添加依赖...原创 2018-11-06 20:40:55 · 298 阅读 · 0 评论 -
Aha!设计模式(6)-抽象工厂(5)
协作• 通常在运行时刻创建(唯一的)一个ConcreteFactory类的实例。这一具体的工厂创建具有特定实现的产品对象。为创建不同的产品对象,客户应使用不同的具体工厂。 原书的翻译有一点问题,根据以下的英文原文,作者在这里加上了一个修饰词“唯一的”,这样更准确。另外这里所谓不同的产品对象应该是另外一组产品对象的意思。 Normally a single instance of...原创 2018-11-07 20:33:24 · 296 阅读 · 0 评论 -
Aha!设计模式(4)-抽象工厂(3)
适用性在以下情况可以使用Abstract Factory模式 • 一个系统要独立于它的产品的创建、组合和表示时。 对于一个一定规模以上的软件,经常会出现需要多个功能组件协同工作的情况。为了降低耦合性,增强扩展性,经常要对系统进行分解。这时将功能组件的创建,组合(协同动作)和表示分离是一种常用的方式。而功能组件的创建部分就可以使用抽象工程模式。 • 一个系统要由多个产品系...原创 2018-11-05 20:55:27 · 334 阅读 · 0 评论 -
Aha!设计模式(8)-抽象工厂(7)
实 现(续) 2) 创建产品 AbstractFactory仅声明一个创建产品的接口 ,真正创建产品是由ConcreteProduct子类实现的。最通常的一个办法是为每一个产品定义一个工厂方法(参见Factory Method(3 . 3))。一个具体的工厂将为每个产品重定义该工厂方法以指定产品。虽然这样的实现很简单,但它却要求每个产品系列都要有一个新的具体工厂子类,即使这些产品系列的差...原创 2018-11-13 19:49:01 · 389 阅读 · 0 评论 -
Aha!设计模式(7)-抽象工厂(6)
实 现 下面是实现Abstract Factor模式的一些有用技术:1) 将工厂作为单件 一个应用中一般每个产品系列只需一个ConcreteFactory的实例。因此工厂通常最好实现为一个Singleton(3.5)。 只有一句话,但是并没有给出实现。为了说明这个问题,作者按照自己的理解,以前面提到的操作系统主题的例子为背景提供一个实现。 类图:有关Singlet...原创 2018-11-12 18:29:26 · 285 阅读 · 0 评论 -
Aha!设计模式(9)-抽象工厂(8)
代码示例 《设计模式》一书中关于代码示例的说明非常详细,这里不再重复原书中的内容。希望大家自己去读一遍原著,然后再来阅读本文的内容。 基本上每个设计模式的代码示例都会讲一个故事,但是故事并不是设计模式的重点,它只是希望大家相信真的存在需要这个模式的场景。重要的还是类关系和代码。 利用者代码: 这段代码中创建了一个Maze对象,两个Room对象和六个Wall对象,...原创 2018-11-14 20:27:39 · 291 阅读 · 0 评论 -
Aha!设计模式(11)-BUILDER(2)
动机《设计模式》中关于BUILDER动机的说明使用的是RTF文档格式转换的例子。这个例子本身很容易理解,这里就不再重复了。本文只讲作者本人的见解。 还是那一招本连载提到过:大部分情况下,设计模式也好,面向对象也好其实就是一招,多态。这个结论对于BUILDER模式同样使用。具体到《设计模式》中的例子,希望变化的就是输出的类型或者说格式。基于这个想法,即使我们没有学习设计模式,也可以进...原创 2018-11-20 19:39:14 · 278 阅读 · 0 评论 -
Aha!设计模式(12)-BUILDER(3)
适用性 在以下情况使用Builder模式• 当创建复杂对象的算法应该独立于该对象的组成部分以及它们的装配方式时。• 当构造过程必须允许被构造的对象有不同的表示时。 一般来讲,创造一个复杂对象的处理总是可以拆分成算法(或步骤)的部分和实际生成构件的部分。无论我们希望独立算法还是替换表现,所做的都是一件事,把算法和生成构件拆分开,这就是Builder模式。 简单说就是,想变...原创 2018-11-21 20:43:42 · 336 阅读 · 0 评论 -
Aha!设计模式(10)-BUILDER(1)
本来抽象工厂模式还有已知应用和相关模式两个模块,但是它们对于理解设计模式没有什么意义,本系列连载会直接省略。 名称还是先看名称。这个设计模式的英文为BUILDER,中文翻译成了“生成器”,作者认为这个翻译不太好,如果翻译成【构建者】,或者【建造者】没准会更好。【生成器】的说法无法给人构建对象很大,很复杂的感觉。例如大楼,轮船等。还是英文的BUILDER最好。 意图将一个复杂...原创 2018-11-19 19:59:01 · 298 阅读 · 0 评论 -
Aha!设计模式(13)-BUILDER(4)
参与者 Builder(TextConverter)— 为创建一个Product对象的各个部件指定抽象接口。•ConcreteBuilder(ASCIIConverter,TeXConverter,TextWidgetConverter)— 实现Builder的接口以构造和装配该产品的各个部件。— 定义并明确它所创建的表示。— 提供一个检索产品的接口(例如, GetASCIITe...原创 2018-11-26 20:21:11 · 283 阅读 · 0 评论 -
Aha!设计模式(17)-BUILDER(8)
实现 通常有一个抽象的Builder类为导向者可能要求创建的每一个构件定义一个操作。这些操作缺省情况下什么都不做。一个ConcreteBuilder类对它有兴趣创建的构件重定义这些操作。 还是那句话,这并不是Builder模式的专利,只要有抽象/具象关系就是这样。 这里是其他一些要考虑的实现问题:1) 装配和构造接口 生成器逐步的构造它们的产品。因此Builder类接口...原创 2018-12-04 20:11:53 · 401 阅读 · 0 评论 -
Aha!设计模式(15)-BUILDER(6)
效果 2) 它将构造代码和表示代码分开。 Builder模式将构建对象的代码和表现(表达)对象的代码隔离开。这里的构建偏向于抽象的指示部分,表现(表达)则偏向实际的输出。例如我们说装一扇门,对于建筑模型来讲,可能就是在模型上粘一个小木板;对于现场工人来讲,可能真的就是安装一个防盗门。这里装一扇门就是抽象的指示,而粘小木板或者安装防盗门则是具象表现(表达)的部分。 Build...原创 2018-11-28 20:13:32 · 310 阅读 · 0 评论 -
Aha!设计模式(18)-BUILDER(9)
实现 2) 为什么产品没有抽象类 通常情况下,由具体生成器生成的产品,它们的表示相差是如此之大以至于给不同的产品以公共父类没有太大意思。在 RTF例子中,ASCIITe xt和TextWidget对象不太可能有公共接口,它们也不需要这样的接口。因为客户通常用合适的具体生成器来配置导向者,客户处于的位置使它知道Builder的哪一个具体子类被使用和能相应的处理它的产品。 这一点和...原创 2018-12-05 18:37:36 · 286 阅读 · 0 评论 -
Aha!设计模式(21)-工厂方法(2)
动机 框架使用抽象类定义和维护对象之间的关系。这些对象的创建通常也由框架负责。面向对象编程很多场合其实就是对抽象类编程。我们可以认为,抽象类+抽象类之间的协作构成了架构。在这样的架构中,通常也会包含对象的创建部分。 考虑这样一个应用框架,它可以向用户显示多个文档。在这个框架中,两个主要的抽象是类Application和Document。这两个类都是抽象的,客户必须通过它们的子类来...原创 2018-12-12 18:58:36 · 282 阅读 · 0 评论 -
Aha!设计模式(16)-BUILDER(7)
效果 3 ) 它使你可对构造过程进行更精细的控制 Builder模式与一下子就生成产品的创建型模式不同,它是在导向者的控制下一步一步构造产品的。仅当该产品完成时导向者才从生成器中取回它。因此Builder接口相比其他创建型模式能更好的反映产品的构造过程。这使你可以更精细的控制构建过程,从而能更精细的控制所得产品的内部结构。 这是Builder模式和工场模式的重要区别之一。工厂模...原创 2018-12-03 18:22:35 · 379 阅读 · 0 评论 -
Aha!设计模式(27)-原型(1)
意图 用原型实例指定创建对象的种类,并且通过拷贝这些原型创建新的对象。 虽然看起来是一件事,但却包含了两个方面:一个是被创建对象种类的表达方式的问题;另一个是创建对象过程的问题。这里的对象种类是一个比较微妙的表达方式,它不一定是类的概念,也有可能只是数据,结构的不同。这里先记下一笔。 动机 你可以通过定制一个通用的图形编辑器框架和增加一些表示音符、休止符和五线谱的新...原创 2018-12-26 17:53:39 · 319 阅读 · 0 评论 -
Aha!设计模式(19)-BUILDER(10)
代码示例 《设计模式》中的示例代码因为不完整所以不能编译,而且还有内存泄漏。它真的就是一个示例。本文根据自己的理解将不足的补上,同时在使用智能指针消除内存泄漏的同时尽量小地变更原来的代码。 首先是接口: 《设计模式》书中将实现代码也写在同一个文件中,这里将它们分开: 这两种方式区别不大。 接下来是使用Builder的代码: 将这个C...原创 2018-12-10 19:02:49 · 302 阅读 · 0 评论 -
Aha!设计模式(22)-工厂方法(3)
4. 适用性 在下列情况下可以使用Factory Method模式:• 当一个类不知道它所必须创建的对象的类的时候。 当一个类需要创建某种对象却无法事先知道它的类型信息的时候。例如前文提到的应用/文档架构。这个架构的使用者是开发人员,开发的应用也成千上万,架构的提供者当然没有办法知道需要创建对象的类型。可以使用工厂方法模式决定所要创建的对象类型。 这种情况是真不知道。 ...原创 2018-12-17 20:09:30 · 318 阅读 · 0 评论 -
Aha!设计模式(20)-工厂方法(1)
意图定义一个用于创建对象的接口,让子类决定实例化哪一个类。 Factory Method使一个类的实例化延迟到其子类。 上文中一共有两句话,前一句没有问题,后一句就没有办法理解了:一个类将它自己的示例话延迟到子类是什么意思呢? 解决的办法还是看原文。 Define an interface for creating an object, but let subclass...原创 2018-12-11 19:18:48 · 286 阅读 · 0 评论 -
Aha!设计模式(23)-工厂方法(4)
5. 结 构光从类图的角度来看,工厂方法和抽象工厂的类图都存在平行的product和creator(或factory)类,不同的是在工厂方法模式中: 每个creator只有一个构建方法。 creator还会有构建方法以外的操作。 作为派生类的ConcretCreator/ConcreateProduct只有一套,也就意味着替换派生类不是这个模式的主要目的。 ...原创 2018-12-18 19:30:57 · 298 阅读 · 0 评论 -
Aha!设计模式(29)-原型(3)
适用性(续) 前一篇文章调整了《设计模式》一书中的译文,结果是文章从字面上更好理解了。但是这还不够,所以本文进一步说明。 Prototype模式的适用场景为:当一个系统应该独立于它的产品创建、构成和表示,而且 先别管那个“而且”,只看前半句。换个说法就是将构建产品的部分从系统的其他功能中分离出来。如果只看这一点的话,抽象工厂模式同样适合。好在后面有一个"而且”,将这一条和下...原创 2019-01-03 19:16:12 · 335 阅读 · 0 评论 -
Aha!设计模式(25)-工厂方法(6)
9. 实 现关于实现的部分,《设计模式》书中的描述已经很详细了,所以这里只进行简单的归纳。 当应用Factory Method模式时要考虑下面一些问题:1) 主要有两种不同的情况 Factory Method模式主要有两种不同的情况: (1)第一种情况是,Creator类是一个抽象类并且不提供它所声明的工厂方法的实现。 (2)第二种情况是,Creator是一个具体的类而且为工厂方...原创 2018-12-24 19:38:42 · 568 阅读 · 0 评论 -
Aha!设计模式(30)-原型(4)
4. 结 构按照UML的规则,prototype应该写在Prototype类一侧,这是《设计模式》一书中的通病。大家在自己画设计模式类图的时候需要注意一下。 5. 参与者 • Prototype(Graphic)— 声明一个克隆自身的接口。• ConcretePrototype(Staff、WholeNote、HalfNote)— 实现一个克隆自身的操作。• C...原创 2019-01-04 18:48:44 · 303 阅读 · 0 评论 -
Aha!设计模式(26)-工厂方法(7)
10. 代码示例 还是迷宫游戏的例子。不同的是这次是MazeGame自己构建迷宫。 由于是工厂方法模式,所以CreateMaze没有硬编码构建Wall,Room,Door等对象,而是分别调用虚函数MakeRoom,MakeRoor,MakeWall对象。 这个准备工作完成以后,我们就可以另外定义不同的游戏: 这两个派生类根据各自需要分别从新定义了M...原创 2018-12-25 19:00:53 · 307 阅读 · 0 评论 -
Aha!设计模式(28)-原型(2)
3. 适用性 当一个系统应该独立于它的产品创建、构成和表示时,要使用Prototype模式;以及• 当要实例化的类是在运行时刻指定时,例如,通过动态装载;或者• 为了避免创建一个与产品类层次平行的工厂类层次时;或者• 当一个类的实例只能有几个不同状态组合中的一种时。建立相应数目的原型并克隆它们可能比每次用合适的状态手工实例化该类更方便一些。 这段译文不大好理解。还是让我们来...原创 2019-01-02 19:44:07 · 421 阅读 · 0 评论 -
Aha!设计模式(31)-原型(5)
7. 效果Prototype有许多和Abstract Factory(3 . 1)和Builder(3 . 2)一样的效果:它对客户隐藏了具体的产品类,因此减少了客户知道的名字的数目。此外,这些模式使客户无需改变即可使用与特定应用相关的类。 隐藏具象类,针对抽象类编程与其说是创建对象模式是的共性,不如说是大多数设计模式的共性。进一步来讲,应该说是面向对象编程这门技术的共性。重要的事情说...原创 2019-01-07 18:46:27 · 339 阅读 · 0 评论 -
Aha!设计模式(40)-单例(6)
实现(续) 2) 创建Singleton类的子类主要问题与其说是定义子类不如说是建立它的唯一实例,这样客户就可以使用它。事实上,指向单件实例的变量必须用子类的实例进行初始化。最简单的技术是在Singleton的Instance操作中决定你想使用的是哪一个单件。代码示例一节中的一个例子说明了如何用环境变量实现这一技术。 《设计模式》中没有提供示例代码,作者认为大致应该如下: ...原创 2019-01-23 18:34:14 · 292 阅读 · 0 评论 -
Aha!设计模式(32)-原型(6)
5) 用类动态配置应用 一些运行时刻环境允许你动态将类装载到应用中。在像 C++这样的语言中,Prototype模式是利用这种功能的关键。 某些开发环境可以(例如通过系列化的方式)在程序执行的时侯加载类。这些类被加载以后的用法可分为两种情况:直接使用和作为生成其他对象的模板。第二中方法的关键就是原型模式。 一个希望创建动态载入类的实例的应用不能静态引用类的构造器。而应该由运...原创 2019-01-08 19:11:41 · 300 阅读 · 0 评论 -
Aha!设计模式(35)-单例(1)
意图 保证一个类仅有一个实例,并提供一个访问它的全局访问点。定义一个类,这个类有且只有一个可以随时访问的实例。这里需要注意的是【保证】这两个字。 动机对一些类来说,只有一个实例是很重要的。确实如此。 虽然系统中可以有许多打印机,但却只应该有一个打印假脱机(printer spooler),只应该有一个文件系统和一个窗口管理器。一个数字滤波器只能有一个A / D转...原创 2019-01-14 18:20:46 · 288 阅读 · 0 评论 -
Aha!设计模式(33)-原型(7)
实现 因为在像C++这样的静态语言中,类不是对象,并且运行时刻只能得到很少或者得不到任何类型信息,所以Prototype特别有用。而在Smalltalk或Objective C这样的语言中Prototype就不是那么重要了,因为这些语言提供了一个等价于原型的东西(即类对象)来创建每个类的实例。Prototype模式在像Self [US87]这样基于原型的语言中是固有的,所有对象的创建都是通...原创 2019-01-09 18:23:38 · 299 阅读 · 0 评论 -
Aha!设计模式(36)-单例(2)
适用性 在下面的情况下可以使用Singleton模式• 当类只能有一个实例而且客户可以从一个众所周知的访问点访问它时。 这句话的翻译有一点点问题,还是看英文原文: there must be exactly one instance of a class, and it must be accessibleto clients from a well-known acce...原创 2019-01-15 18:16:33 · 251 阅读 · 0 评论 -
Aha!设计模式(38)-单例(4)
实现 关于单例模式,《设计模式》一书进行了非常详尽的说明,以至于作者基本上插不上什么话。 下面是使用Singleton模式时所要考虑的实现问题:1) 保证一个唯一的实例Singleton模式使得这个唯一实例是类的一般实例,但该类被写成只有一个实例能被创建。 Singleton模式提供的类的唯一实例本身就是一个一般的实例,只是通过实现层面保证只有一个实例被创建。 ...原创 2019-01-21 18:29:36 · 273 阅读 · 0 评论 -
Aha!设计模式(46)-适配器(3)
适用性 以下情况使用Adapter模式• 你想使用一个已经存在的类,而它的接口不符合你的需求。 这种情况就是适配器模式开头部分讲过的例子。我们想使用一个已经存在的类,但是又不想(也不应该)修改那个类的接口时可使用适配器模式。这属于被动适配。 • 你想创建一个可以复用的类,该类可以与其他不相关的类或不可预见的类(即那些接口可能不一定兼容的类)协同工作。 设想我们在...原创 2019-01-31 18:22:59 · 274 阅读 · 0 评论 -
Aha!设计模式(37)-单例(3)
效果Singleton模式有许多优点:1) 对唯一实例的受控访问 因为Singleton类封装它的唯一实例,所以它可以严格的控制客户怎样以及何时访问它。 对于数据的访问控制,一般都要解决哪个数据,什么时候被访问的问题。这两个问题中,那个数据的问题更加重要。单例模式保证只有一个可供使用的实例,剩下的监控就变得很简单。 2) 缩小名空间 Singleton模式是对全局变量...原创 2019-01-16 18:20:04 · 330 阅读 · 0 评论 -
Aha!设计模式(39)-单例(5)
多线程环境下的单例模式 首先谢谢【小灰灰】同学的留言,还真没有注意到C++11中static变量线程安全这个新特性这个在单例模式中使用。于是有了本文。 昨天实例代码中Instance方法是这样实现的: 这段代码要想在多线程环境下使用需要多少花一些功夫的。具体做法大家只要搜索【C++】,【单例模式】,【多线程】就能发现大量的文章,这里就不再赘述了。文章中提到的方...原创 2019-01-22 18:43:35 · 287 阅读 · 0 评论 -
Aha!设计模式(44)-适配器(1)
意图 将一个类的接口转换成客户希望的另外一个接口。 Adapter模式使得原本由于接口不兼容而不能一起工作的那些类可以一起工作。适配器这个名称非常好,读者可以考虑电源插头转换器,接下来我们会不断地重复这个类比。 动机 有时,为复用而设计的工具箱类不能够被复用的原因仅仅是因为它的接口与专业应用领域所需要的接口不匹配。 提供一个可以复用的类库或者函数库一般来讲并不是...原创 2019-01-29 18:31:03 · 364 阅读 · 0 评论 -
Aha!设计模式(34)-原型(8)
代码示例 用的还是MazeGame的例子。首先定义一个MazeFactory的子类MazePrototypFacoty,这个继承关系本身是抽象工厂模式。 这个子类使用原型模式构建产品,其构造函数如下: 在构建产品时,使用原型的Clone方法。 代码中使用Initialize/setNumber方法来修改克隆之后对象的属性。这种情况在实际的...原创 2019-02-21 19:18:34 · 350 阅读 · 0 评论