结构模式

可用

2.1 适配器

适配器(Adapter)是一种结构设计模式,旨在通过专门创建的接口来组织对象的功能的使用,这些对象不可用于修改。

官方定义有点棘手,但如果用自己的话来说,适配器就是一种设计模式,它允许具有不兼容接口的对象一起工作

适配器模式

用于组织对象功能的使用,这些功能不能通过专门创建的接口进行修改。创建了一个具有所需接口的附加类,该类又调用所需对象(没有所需接口)的方法。

重要的!如果在代码中您遇到类的后缀 Adapter,那么您完全有权利认为该类充当适配器并且与根据上述方案工作的一组类相关联。

它用于系统支持所需数据和行为但具有不适当接口的情况。Adapter 模式最常见的用途是创建一个继承自新的或现有抽象类的类。

优势:

  • 过渡到使用其他外部类不需要改造系统本身,多实现一个 Adapter 类就足够了。
  • 独立于外部类的实现(我们无法更改其代码的库中的类)。您的程序变得独立于外部类的接口。

2.2 装饰器

装饰器是一种结构设计模式,用于动态地将附加行为附加到对象。装饰器模式为通过子类化来扩展功能的做法提供了一个很好且灵活的替代方案。

装饰者模式

用于将附加义务动态连接到对象。

你们中的许多人会问:如何动态地(在程序运行时)向对象添加新行为?一个物体可以由碎片组装而成,也就是小物体。还记得 servlet 中的过滤器链吗?还是使用 filter()、map()、list() 编写查询时的 Stream API?

IntStream.of(50, 60, 70, 80, 90).filter(x -> x < 90).map(x -> x + 10).limit(3).forEach(System.out::print);

装饰者模式的优点:

  • 无需创建子类来扩展对象的功能。
  • 在任何地方动态连接新功能的能力:在 ConcreteComponent 对象的主要功能之前或之后。

2.3 代理

代理是一种结构设计模式,它提供一个对象来控制对另一个对象的访问,拦截并传递它的所有调用。

代理人(Proxy)

代理模式提供了一个替代对象来代替真实对象。该对象控制对原始对象的访问。经常使用。

还记得我们如何使用 Mockito 框架并使用 Mockito.spy() 方法或 @Spy 注释拦截对真实对象的调用吗?就在那时创建了一个特殊的 Proxy 对象,通过它传递对原始对象的所有调用。

然后我们可以通过向对象添加规则来管理这些调用。没错——原始对象没有改变,使用它变得更加灵活。当我们不从我们的代码中调用代理对象,而是将它传递到某个地方时,它特别有用。从而控制两个独立于我们的对象的通信。

按用途分类的代理类型:

  • 记录代理:记录所有对“主题”的调用及其参数。
  • 远程代理(remote proxies):提供与位于不同地址空间或远程机器上的“Subject”的通信。它还可能负责对请求及其参数进行编码,并将编码后的请求发送给真正的“主题”。
  • 虚拟代理(virtual proxies):保证​​真正的“Subject”只在真正需要的时候才被创建。它还可以缓存一些关于真实“Subject”的信息来延迟它的创建。
  • Copy-on-write:当客户端执行某些操作时提供“主题”的副本(“虚拟代理”的特例)。
  • 保护代理:可以检查调用者是否具有发出请求所需的权限。
  • 缓存代理:在将计算结果提供给可以共享结果的多个客户端之前提供计算结果的临时存储。
  • 筛选代理:保护“主题”免受危险客户的侵害(反之亦然)。
  • Synchronization Proxy:在异步多线程环境中对“Subject”进行同步访问控制。
  • “智能”链接(智能引用代理):创建指向“主题”的链接时执行其他操作,例如,计算指向“主题”的活动链接数。

2.4 桥梁

桥接模式是一种结构设计模式,用于“分离抽象和实现,使它们可以独立改变”。

桥接模式使用封装、聚合,可以使用继承来分担类之间的责任。

桥

当抽象和实现分离时,它们可以独立改变。换句话说,当通过桥接模式实现时,改变接口的结构不会干扰改变实现的结构。

将这样的抽象考虑为图形。形状有很多种,每一种都有自己的属性和方法。但是,有一些东西可以将所有数字结合在一起。例如,每个形状必须能够绘制自身、缩放等。

同时,根据操作系统或图形库的类型,绘制图形可能会有所不同。形状应该能够在各种图形环境中自行绘制。但是在每个形状中实现所有的绘制方法,或者每次绘制方法改变时都修改形状是不切实际的。

在这种情况下,桥接模式会有所帮助,它允许您创建将在各种图形环境中实现绘图的新类。使用这种方法,可以很容易地添加新形状和绘制它们的方法。

图中箭头表示的连接可以有 2 种含义:a) “一种”,根据 Liskov 替换原则,和 b) 抽象的可能实现之一。语言通常使用继承来实现 a) 和 b),这往往会使类层次结构膨胀。

桥正是为了解决这个问题:对象是由层次结构 A 和层次结构 B 的类的对象成对创建的,层次结构 A 内的继承根据 Liskov 具有“多样性”的含义,对于“实现”的概念抽象”使用了从对象 A 到其配对对象 B 的链接。

2.5 门面

Facade 模式是一种结构设计模式,它通过减少对单个对象的所有可能的外部调用来隐藏系统的复杂性,该对象将它们委托给系统中的适当对象。

门面模板

如果不需要与子系统的强耦合,或者子系统的实现可能会发生变化,如何为子系统提供具有一组不同实现或接口的统一接口?

定义一个与子系统的交互点——一个外观对象,它提供与子系统的公共接口,并赋予它与其组件交互的责任。外观是一个外部对象,它为子系统服务提供单一入口点。

其他子系统组件的实现是私有的,对外部组件不可见。Facade 对象提供了一个 GRASP 模式的实现 Resistant to changes 在保护子系统实现中免受变化方面。

重要的!当我们想要完全隐藏某些对象组并通过我们的对象传递与它们的所有通信时,使用此模式。如果你只是想对对象的通信过程提供一些控制而不一定要隐藏它们,那么最好使用代理模式。

1
任务
模块 3,  第 16 级课程 1
已锁定
Through the Nail with a Microscope
task4101
1
任务
模块 3,  第 16 级课程 1
已锁定
Signature Recipe
task4102
1
任务
模块 3,  第 16 级课程 1
已锁定
Surprise, Anonymous!
task4103
1
任务
模块 3,  第 16 级课程 1
已锁定
Fantastic Creatures
task4104
1
任务
模块 3,  第 16 级课程 1
已锁定
Alchemy Library
task4105
评论
  • 受欢迎
你必须先登录才能发表评论
此页面还没有任何评论