中介者模式
本博客大部分内容来于免费在线学习设计模式
1:中介者模式中介者模式是一种行为设计模式,能让你减少对象之间混乱无序的依赖关系。该模式会限制对象之间的直接交互,迫使它们通过一个中介者对象进行合作。
2:中介者模式问题在现实生活中,常常会出现好多对象之间存在复杂的交互关系,这种交互关系常常是“网状结构”,它要求每个对象都必须知道它需要交互的对象。例如,每个人必须记住他(她)所有朋友的电话;而且,朋友中如果有人的电话修改了,他(她)必须让其他所有的朋友一起修改,这叫作“牵一发而动全身”,非常复杂。
3:中介者模式解决方案中介者模式建议你停止组件之间的直接交流并使其相互独立。这些组件必须调用特殊的中介者对象,通过中介者对象重定向调用行为,以间接的方式进行合作。最终,组件仅依赖于一个中介者类,无需与多个其他组件相耦合。
如果把这种“网状结构”改为“星形结构”的话,将大大降低它们之间的“耦合性”,这时只要找一个“中介者”就可以了。如前面所说的“每个人必须记住所有朋友电话”的问题,只要在网上建立一个每个朋友都可以访问的“通信录”就解决了。这样的例子还有很多,例如,你刚刚参加工作想租房,可以找“房屋 ...
单例模式
本博客大部分内容来于免费在线学习设计模式
1:单例模式单例模式是一种创建型设计模式,让你能够保证一个类只有一个实例,并提供一个访问该实例的全局节点。
2:单例模式问题单例模式同时解决了两个问题。所以违反了单一职责原则。
保证一个类只有一个实例。(eg:控制某些共享资源 (例如数据库或文件) 的访问权限。)
为该实例提供一个全局访问节点。例如存储重要对象的全局变量,它们在使用上十分方便,但同时也非常不安全,因为任何代码都有可能覆盖掉那些变量的内容,从而引发程序崩溃。
例:一个国家只有一个政府,不管身份是什么,而”某政府“就像全局访问节点一样。
3:单理模式结构
单例 (Singleton) 类声明了一个名为 getInstance获取实例的静态方法来返回其所属类的一个相同实例。
单例的构造函数必须对客户端 (Client) 代码隐藏。调用 获取实例方法必须是获取单例对象的唯一方式。
代码示例:
单例模式有多种创建方法:
这里列举三种:
通过枚举类型创建单例
12345public enum Singleton { INSTANCE; p ...
工厂方法模式
本博客大部分内容来于免费在线学习设计模式
1:工厂方法模式工厂方法模式是一种创建型设计模式,其在父类中提供一个创建对象的方法,允许子类决定实例化对象的类型。
2:工厂方法模式问题举个例子:假如你现在需要不同类型的水果:例如苹果,香蕉,梨等等。现在如果没有淘宝,水果摊这一类能提供多种水果的“工厂”。那么你买苹果需要去找苹果园,买香蕉需要去找香蕉生产地,每一个水果都需要你自行联系对应的水果生成地。很麻烦不是吗,想一想水果摊这一类的“工厂”是怎么解决这问题的?
再举一个例子:
如果你开发了一款物流管理应用。假设每一种运输方法类的构建都很复杂,需要编写大量代码。在初始版本只支持一种运输方案:卡车,于是你选择直接调用多个方法来创建卡车类。后来你需要增加另一个方式:轮船。代码部分该如何处理呢?继续直接创建一个轮船类吗。那么创建轮船类的大量代码将到处都是。更糟糕的是,如果你以后需要在程序中支持另外一种运输方式,很可能需要再次对这些代码进行大幅修改。
最后,你将不得不编写繁复的代码,根据不同的运输对象类,在应用中进行不同的处理。
3:工厂方法模式解决方案工厂方法模式建议使用特殊的工厂方法代替对于对 ...
抽象工厂模式
本博客大部分内容来于免费在线学习设计模式
1:抽象工厂模式抽象工厂(AbstractFactory)模式是一种为访问类提供一个创建一组相关或相互依赖对象的接口,且访问类无须指定所要产品的具体类就能得到同族的不同等级的产品的模式结构。
2:抽象工厂模式问题工厂方法模式考虑的是一类产品的生产,如畜牧场只养动物、电视机厂只生产电视机、计算机软件学院只培养计算机软件专业的学生等。
但是在现实生活中许多工厂是综合型的工厂,能生产多等级(种类) 的产品,如农场里既养动物又种植物,电器厂既生产电视机又生产洗衣机或空调,大学既有软件专业又有生物专业等。
而抽象工厂模式将考虑多等级产品的生产。将同一个具体工厂所生产的位于不同等级的一组产品称为一个产品族,
3:抽象工厂模式解决方案首先,抽象工厂模式建议为系列中的每件产品明确声明接口。然后确保所有产品变体都继承这些接口,例如(所有品牌的电视机都继承电视机接口,所有品牌的空调都继承空调接口)
然后声明抽象工厂–包含系列中所有产品构造方法的接口。例如:createWasher(创建洗衣机),createTV(创建电视机)…这些方法必须返回抽象产品类型,即我 ...
生成器模式
本博客大部分内容来于免费在线学习设计模式
1:生成器模式生成器模式是一种创建型设计模式,使你能够分步骤创建复杂对象。该模式允许你使用相同的创建代码生成不同类型和形式的对象。
2:生成器模式问题在软件开发过程中有时需要创建一个复杂的对象,这个复杂对象通常由多个子部件按一定的步骤组合而成。例如,计算机是由 OPU、主板、内存、硬盘、显卡、机箱、显示器、键盘、鼠标等部件组装而成的,采购员不可能自己去组装计算机,而是将计算机的配置要求告诉计算机销售公司,计算机销售公司安排技术人员去组装计算机,然后再交给要买计算机的采购员。生活中这样的例子很多,如游戏中的不同角色,其性别、个性、能力、脸型、体型、服装、发型等特性都有所差异;还有汽车中的方向盘、发动机、车架、轮胎等部件也多种多样;每封电子邮件的发件人、收件人、主题、内容、附件等内容也各不相同。
解决这些问题最简单的方法是扩展基类,然后创建一系列覆盖所有参数组合的子类。但最终你将面对相当数量的子类。任何新增的参数都会让这个层次结构更加复杂。
另一种方法则无需生成子类。你可以在房屋基类中创建一个包括所有可能参数的超级构造函数,并用它来控制房屋对象 ...
代理模式
本博客大部分内容来于免费在线学习设计模式
1:代理模式(Proxy)代理模式是一种结构型设计模式,让你能够提供对象的替代品或其占位符。代理控制着对于目标对象的访问,并允许在将请求提交给对象前后进行一些处理。
2:代理模式问题为什么要控制对于某个对象的访问呢?举个例子:有这样一个消耗大量系统资源的巨型对象,你只是偶尔需要使用它,并非总是需要。
或者给对象添加功能:在理想情况下,我们希望将代码直接放入对象的类中进行修改,但这并非总是能实现:比如类可能是第三方封闭库的一部分。所以我们也需要代理对象来添加功能
3:代理模式解决方案代理模式建议新建一个与原目标对象接口相同的代理类,然后更新应用以将代理对象传递给所有原始对象客户端。代理类接收到客户端请求后会创建实际的目标对象,并将所有工作委派给它。
这有什么好处呢?
如果需要在类的主要业务逻辑前后执行一些工作,你无需修改类就能完成这项工作。
由于代理实现的接口与原类相同,因此你可将其传递给任何一个使用实际服务对象的客户端。
例:
信用卡是银行账户的代理,银行账户则是一大捆现金的代理。它们都实现了同样的接口,均可用于进行支付。你通过信用 ...
享元模式
本博客大部分内容来于免费在线学习设计模式
1:享元模式享元模式是一种结构型设计模式, 它摒弃了在每个对象中保存所有数据的方式, 通过共享多个对象所共有的相同状态, 让你能在有限的内存容量中载入更多对象。
2:享元模式问题在面向对象程序设计过程中,有时会面临要创建大量相同或相似对象实例的问题。创建那么多的对象将会耗费很多的系统资源,它是系统性能提高的一个瓶颈。例如,围棋和五子棋中的黑白棋子,图像中的坐标点或颜色,局域网中的路由器、交换机和集线器,教室里的桌子和凳子等。这些对象有很多相似的地方,如果能把它们相同的部分提取出来共享,则能节省大量的系统资源,这就是享元模式的产生背景。
3:享元模式解决方案在黑白棋子,坐标点这些类中,你会发现一些成员变量储存的值是相同的,而每个粒子的另一些状态(坐标,颜色等)是不同的。
对象的常量数据通常被称为内在状态(即不会随着环境的改变而改变的可共享部分), 其位于对象中,其他对象只能读取但不能修改其数值。而对象的其他状态常常能被其他对象 “从外部” 改变,因此被称为外在状态(随环境改变而改变的不可以共享的部分)。
享元模式建议不在对象中存储外在状态,而 ...
组合模式
本博客大部分内容来于免费在线学习设计模式
1:组合模式组合模式是一种结构型设计模式,又叫部分整体模式,是用于把一组相似的对象当作一个单一的对象,你可以使用它将对象组合成树状结构,并且能像使用独立对象一样使用它们。
2:组合模式问题如果应用的核心模型能用树状结构表示,在应用中使用组合模式才有价值。
例如,你有两类对象:产品和盒子。一个盒子中可以包含多个产品或者几个较小的盒子。这些小盒子中同样可以包含一些产品或更小的盒子,以此类推。
在这些类的基础上你需要开发一个订单系统。订单中可以包含无包装的简单产品,也可以包含装满产品的盒子……以及其他盒子。如何计算订单的总价呢?
在现实生活中,可以直接拆开盒子,直接计算每个产品的价格。而在程序中,你必须知道所有产品和盒子的细节,知道盒子的嵌套层数以及其他详细信息,才能计算出总价。因此直接计算是不可行。
在现实生活中,存在很多“部分-整体”的关系,例如,大学中的部门与学院、总公司中的部门与分公司、学习用品中的书与书包、生活用品中的衣服与衣柜以及厨房中的锅碗瓢盆等。在软件开发中也是这样,例如,文件系统中的文件与文件夹、窗体程序中的简单控件与容器控件 ...
装饰模式
本博客大部分内容来于免费在线学习设计模式
1:装饰模式装饰模式是一种结构型设计模式,允许你通过将对象放入包含行为的特殊封装对象中来为原对象绑定新的行为。即在不改变现有对象结构的情况下,动态地给该对象增加一些职责(即增加其额外功能)。
2:装饰模式问题假设你正在开发一个提供通知功能的库,其他程序可使用它向用户发送关于重要事件的通知。
库的最初版本基于通知器(Notifier)类,其中只有很少的几个成员变量,一个构造函数和一个send发送方法。该方法可以接收来自客户端的消息参数,并将该消息发送给一系列的邮箱,邮箱列表则是通过构造函数传递给通知器的。作为客户端的第三方程序仅会创建和配置通知器对象一次,然后在有重要事件发生时对其进行调用。
在不断发展后,有些用户希望使用微信通知,使用QQ通知,又或者使用短信通知。最简单的方法是: 扩展通知器类,然后在新的子类中加入额外的通知方法。现在客户端要对所需通知形式的对应类进行初始化,然后使用该类发送后续所有的通知消息。
但如果用户希望组合不同的方式,如果创建特殊子类来整合的话,代码量会迅速膨胀。而且不仅是程序库,客户端也是如此。
3:装饰模式解决方 ...
适配器模式
本博客大部分内容来于免费在线学习设计模式
1:适配器模式适配器模式是一种结构型设计模式,它能使接口不兼容的对象能够相互合作。它结合了两个独立接口的功能。
这种模式涉及到一个单一的类,该类负责加入独立的或不兼容的接口功能。
2:适配器模式问题例如你开发了一个程序,能从不同来源获取xml格式信息。在开发过程中,你决定整合一个第三方分析库,但是第三方分析库只兼容json格式。也许你可以修改第三方库来支持json,但是这需要修改很多代码,甚至你可能无法修改第三方库。
该如何导出数据呢?
3:适配器模式解决方案适配器是一个特殊的对象,能够转换对象接口,使其能与其他对象进行交互。
适配器模式通过封装对象将复杂的转换过程隐藏于幕后。被封装的对象甚至察觉不到适配器的存在。
适配器不仅可以转换不同格式的数据,其还有助于采用不同接口的对象之间的合作。它的运作方式如下:
适配器实现与其中一个现有对象兼容的接口。
现有对象可以使用该接口安全地调用适配器方法。
适配器方法被调用后将以另一个对象兼容的格式和顺序将请求传递给该对象。
有时候你还可以写一个双向适配器来实现双向转换调用
例:出国旅行时,不同国家 ...