相较而言,责任链模式是一个使用频率很高的模式,大家在日常的开发过程中,也可能会经常遇到,下面,我们就一起来了解一下责任链模式的内容。 一、模式原理分析 责任链模式的原始定义是:通过为多个对象提供处理请求的机会,避免将请求的发送者与其接收者耦合。链接接收对象并沿着链传递请求,直到对象处理它。 这个定义读起来还是有点抽象难懂,实际上它只说了一个关键点:通过构建一个处理流水线来对一次请求进行多次的处理。
命令模式使用频率不算太高,这里大家可能会问:命令和查询有什么区别?简单来说,查询是获取一个不可变的结果,而命令是改变状态,不一定获取结果。 如果你熟悉函数式编程的话,会发现命令模式完全没有使用的必要,甚至在业务开发的场景中也很少使用到。不过对于想要找到正确抽象的设计者来说,命令模式的设计思想却非常值得借鉴。 一、模式原理分析 命令模式的原始定义是:将一个请求封装为一个对象,从而让我们可以参数化具有
解释器模式使用频率不算高,通常用来描述如何构建一个简单“语言”的语法解释器。它只在一些非常特定的领域被用到,比如编译器、规则引擎、正则表达式、SQL 解析等。不过,了解它的实现原理同样很重要,能帮助我们思考如何通过更简洁的规则来表示复杂的逻辑。 一、模式原理分析 解释器模式的原始定义是:用于定义语言的语法规则表示,并提供解释器来处理句子中的语法。 语法也称文法,在语言学中指任意自然语言中句子、短语
迭代器模式是我们学习一个设计时很少用到的、但编码实现时却经常使用到的行为型设计模式。在绝大多数编程语言中,迭代器已经成为一个基础的类库,直接用来遍历集合对象。在平时开发中,我们更多的是直接使用它,很少会从零去实现一个迭代器。今天,我们就一起来看看迭代器模式的原理和实现,帮助大家更好理解。 一、模式原理分析 迭代器模式又叫游标(Cursor)模式,它的原始定义是:迭代器提供一种对容器对象中的各个元素
中介者模式理解起来并不难,代码实现简单,学习难度也很小,只要合理充分地应用这个模式,往往就能够解决一些意想不到的问题。那这到底是怎样一个模式?多用于什么场景中?为什么使用?该怎么使用?下面我们一起来看看吧。 一、模式原理分析 中介者模式的原始定义是:中介者对象封装了一组对象之间的交互,这组对象会将它们的交互委托给中介者对象,而不是直接交互。 可以看到,这个定义是难得的简单和明确,中介者对象就是用于
相较于其他的设计模式,备忘录模式不算太常用,但好在这个模式理解、掌握起来并不难,代码实现也比较简单,应用场景就更是比较明确和有限,一般应用于编辑器或会话上下文中防丢失、撤销、恢复等场景中。下面就一起来了解一下吧。 一、模式原理分析 备忘录模式的原始定义是:捕获并外部化对象的内部状态,以便以后可以恢复,所有这些都不会违反封装。 这个定义是非常简单的,我们可以直接来看看备忘录模式对应的 UML 图:
观察者模式是一种非常流行的设计模式,也常被叫作订阅-发布模式。观察者模式在现代的软件开发中应用非常广泛,比如,商品系统、物流系统、监控系统、运营数据分析系统等。 现在我们常说的基于事件驱动的架构,其实也是观察者模式的一种最佳实践。当我们观察某一个对象时,对象传递出的每一个行为都被看成是一个事件,观察者通过处理每一个事件来完成自身的操作处理。 一、模式原理分析 观察者模式的原始定义是:定义对象之间的
状态模式的应用场景非常广泛,比如,线上购物订单、手机支付、音乐播放器、游戏、工作流引擎等场景。状态模式设计的初衷是应对同一个对象里不同状态变化时的不同行为的变化。那么,当我们遇见类似的场景时,该如何来使用状态模式呢?下面我们一起来看看吧 一、模式原理分析 状态模式的原始定义是:允许一个对象在其内部状态改变时改变它的行为,对象看起来似乎修改了自己的类一样。 这个定义确实有点抽象,简单来说,状态模式就
策略模式在实际的开发中很常用,最常见的应用场景是利用它来替换过多的 if-else 嵌套的逻辑判断。除此之外,它还能结合工厂模式给客户端提供非常灵活的使用体验。下面,我们一起来看看吧! 一、模式原理分析 策略模式的原始定义是:定义一系列算法,封装每个算法,并使它们可以互换。策略让算法独立于使用它的客户端而变化。 在这个定义中,策略模式明确表示应当由客户端自己决定在什么样的情况下使用哪些具体的策略。
今天我们先来看一个原理看似很简单,但是理解起来有一定难度,使用场景相对较少的行为型模式:访问者模式。 一、模式原理分析 访问者模式的原始定义是:允许在运行时将一个或多个操作应用于一组对象,将操作与对象结构分离。 这个定义会比较抽象,但是我们依然能看出两个关键点:一个是运行时使用一组对象的一个或多个操作,比如,对不同类型的文件(.pdf、.xml、.properties)进行扫描;另一个是分离对象的
代理模式的原理非常简单,它和装饰模式很类似,都是在不改变同一个接口功能的前提下,对原有接口功能做扩展。但是代理模式的应用却比装饰模式更为广泛,因为代理模式并不执着于链式结构,而是采用更为灵活的单一结构,在很多框架和组件的设计里都能看到代理模式的身影,比如,JDK 的动态代理机制、Spring 的 AOP 机制、Dubbo 框架等。 那么,为什么代理模式能够获得如此广泛的应用呢?下面我们一起来看看。
享元模式的原理和实现都很简单,但是应用场景却相对狭窄,它和现在我们所熟知的缓存模式、池化模式有所联系,却又有不同。看完这篇文章后,相信你会找到这个不同之处。 一、模式原理分析 享元模式的原始定义是:摒弃了在每个对象中保存所有数据的方式,通过共享多个对象所共有的相同状态,从而让我们能在有限的内存容量中载入更多对象。 从这个定义中你可以发现,享元模式要解决的核心问题就是节约内存空间,使用的办法是找出相
你是不是经常把门面模式和代理模式搞混淆?比如,业务 API 网关和 Nginx 网关是不是差不多?实际上这两种模式的本质原理是不同的。相信通过今天的文章,会帮助你找到一个更准确的答案。 一、模式原理分析 门面模式的原始定义是:为子系统中的一组接口提供统一的接口。它定义了一个更高级别的接口,使子系统更易于使用。 这个定义告诉我们门面模式的本质就是统一多个接口的功能。换句话说,当我们需要用更统一的标准
在前面几篇中,我们已经了解了结构型模式中的适配器模式、桥接模式和组合模式。本篇我们要介绍的装饰模式看上去和适配器模式、桥接模式很相似,都是使用组合方式来扩展原有类的,但其实本质上却相差甚远呢。 简单来说,适配器模式侧重于转换,而装饰模式侧重于动态扩展;桥接模式侧重于横向宽度的扩展,而装饰模式侧重于纵向深度的扩展。那么装饰模式到底有哪些需要我们重点学习的地方呢?下面,我们一起来看看吧 一、模式原理分
如果单纯从字面上来看,我们很容易将“组合模式”和“组合关系”搞混。组合模式最初只是用于解决树形结构的场景,更多的是处理对象组织结构之间的问题。而组合关系则是通过将不同对象封装起来完成一个统一功能。 虽然组合模式并不常用,但是学习它的原理能够帮助我们获得更多复杂结构上的思考。比如,MySQL 的索引设计中就是用了 B+ 树算法的组合模式设计,极大地提升了数据查询时的性能。组合模式的原理很容易理解,但
桥接模式的原理非常简单,但是使用起来会有一定的难度,所以相对于适配器模式来说,在理解桥接模式时,重点要能跳出局部,多从整体结构上去思考。 一、模式原理分析 桥接模式的定义是:将抽象部分与它的实现部分分离,使它们都可以独立地变化。 不过,这里的抽象常常容易被理解为抽象类,并将实现理解为继承后的“派生类”,但是这样理解存在局限性,因为 GoF 的本意是想表达“从对象与对象间的关系去看,做抽象实体与抽象
如果说创建型设计模式的关注重点在于一个对象内部结构的话(常常是接口与实现的组合),那么结构性设计模式的关注重点就在于多个对象之间的组合方式。 结构型设计模式一共包括七种:适配器模式、桥接模式、组合模式、装饰模式、门面模式、享元模式和代理模式。今天我们主要来聊聊最常用到的适配器模式。 一、模式原理分析 适配器模式的原始定义是:将类的接口转换为客户期望的另一个接口,适配器可以让不兼容的两个类一起协同工
原型模式最早出现于 1963 年的一个叫 Sketchpad 的系统中,说起 Sketchpad 你可能并不熟悉,但是说起 CAD(计算机辅助设计),现在在工程设计领域几乎无人不知,其实 Sketchpad 就被认为是现代 CAD 程序的鼻祖,主要思想是拥有一张可以实例化成许多副本的原图,如果用户更改了主工程图,则所有实例也会更改。这便是原型模式最初的思维模型。 不过在面向对象编程中,对象的原型在
今天我们接着来看另外一个工厂模式:工厂方法模式**(Factory Method Pattern)**。 工厂方法模式就是我们俗称的工厂模式,和抽象工厂模式很类似,但工厂方法模式因为只围绕着一类接口来进行对象的创建与使用,使用场景更简单和单一,在实际的项目中使用频率反而比抽象工厂模式更高。 一、模式原理分析 工厂方法模式的原始定义是:定义一个创建对象的接口,但让实现这个接口的类来决定实例化哪个类。
在 GoF 的《设计模式》一书中,工厂模式被分为了三种:简单工厂、工厂方法和抽象工厂。(不过,在书中作者将简单工厂模式看作是工厂方法模式的一种特例。)在实际工作中,用得比较多的就是工厂方法模式和抽象工厂模式这两类。本篇文章,我们就先看一下抽象工场模式。 学习抽象工厂模式真正的重点和难点在于:如何找到正确的抽象。虽然抽象工厂模式很容易实现,但更重要的是我们要能意识到“正确的抽象往往都很简单也很底层”
事实上,建造者模式的代码实现非常简单,原理掌握起来也不难,而难点就在于什么时候采用它。比如,经常会遇到的以下两个问题: 为什么直接使用构造函数或者使用 set 方法来创建对象不方便? 为什么一定需要建造者模式来创建? 一、建造者模式分析 在 GoF 的书中,建造者模式的定义是这样的: 将复杂对象的构造与其表示分离,以便同一构造过程可以创建不同的表示。 接下来我们再来看建造者模式的通
一、设计模式的底层逻辑 关于设计模式,大家可能会说: 学习了很多设计模式的课程和文章,依然不会用设计模式; 设计模式适用场景没有设计原则多; 设计模式入门简单,精通很难; 设计模式太复杂看不懂; 面试前才会看设计模式; 设计模式不如面向搜索编程有用; ... 不可否认,一方面大家都很重视设计模式的学习,另一方面却又总是被设计模式搞晕,原因就在于没有真正明白设计模式最
无论是架构设计还是编码实现,现在都越来越离不开接口设计,接口可以说是新时代的“集装箱”,是得到了几乎所有人一致共识的通用标准。 GoF 在很多年前便建议大家应该针对接口编程,原因其实就是为了降低编程变化而导致风险出现的概率。 不过现实中,你可能遇见的更多是这样的情况: 定义好的 API 接口,却接收了额外的参数,导致程序异常退出; 查询返回的数据,没有回传预期的格式,数据处理出错; 一
关注点分离原则是一个帮助我们将复杂问题拆分成小问题的好方法。 什么是关注点?简单来说,在计算机科学中,关注点是能对程序代码产生影响的一组特定信息。比如,在面向对象编程中将关注点描述为对象,在面向函数编程中将关注点描述为函数,在架构设计中将模块、组件、框架描述为关注点,等等。 其实,在前面的文章里,我们也或多或少涉及了关注点分离原则的具体实践。比如,在分层架构中按照服务类型来划分层,层就被作为一个关
在软件开发中,你是不是经常因为沟通效率低下而烦恼? 所接手的维护项目代码质量低,频繁出问题,不得不一次又一次地找之前的人沟通; 团队中模块分散,各自编程风格不同,使用对方服务时需要反复沟通; 跨团队合作沟通,技术栈不同,需要反复沟通统一的标准。 你会发现,这些问题的本质其实都是因为代码而产生了学习成本和沟通成本,或者说,每一份代码都变成了需要重新学习的东西,自然需要反复研究和沟通。
在实际的研发工作中,你是不是遇见过以下场景? 一个平台系统,需要接入各种各样的业务系统,而这些业务系统都有自己的账号体系,平台需要兼容这些系统的账号体系,于是代码中出现了大量依赖于各种账号体系的代码。 一个网站页面,需要越来越多的频道(首页、搜索、分类等),不同频道对应的个性化需求各不相同,并且各种页面的标准组件、布局、模板,以及与后端交互框架也各不相同,不同体系的代码依赖非常紧密。
说到面向对象编程,有一个原则几乎每个程序员都知道,那就是 SOLID 原则。关于它的资料介绍也非常丰富,实践例子也很多。但实际上你很可能把 SOLID 原则都用错了,并且还无意识地一直在滥用它。 之所以这么说,一方面是因为很多时候你都将每一个原则分开使用,容易造成过度解读。比如,在使用接口隔离原则时容易只关心接口,而忽略不同实现,或者不关心接口之间的关系以及和整体系统之间的关系。另一方面是因为它总
在面向对象编程中,你是不是经常听到“要实现代码间的职责分离”,但是具体什么样的代码才算得上是清晰的职责分离,似乎却又总是模糊不清。比如: 代码模块越多职责越清晰? 按照需求来分配职责就是职责分离? 模块化就是职责分离? 实际上,要想写出“职责分离”的代码,单从字面含义是很难下手的,因为业界并没有统一的通用标准。比如,什么是职责分离?为什么职责分离很重要?具体如何实现职责分离? 所以
维护代码是程序员非常重要的日常工作之一,那么你是否曾遇见过以下问题? 接手维护项目,却发现文档缺失、代码无注释,加上维护人离职,基本只能靠猜来梳理代码逻辑。 代码风格过于抽象(命名过短、魔鬼数字、重名方法等),看不懂,也不敢轻易修改。 运行代码出现故障时,不打日志,不抛异常,导致定位问题需要耗费很长时间。 大段的if-else代码嵌套组合,调用逻辑复杂冗长,扩展性差,重构优化费时、
Copyright © 2005-2024 51CTO.COM 版权所有 京ICP证060544号