转载自 树形结构的处理——组合模式(四)

1 透明组合模式与安全组合模式

通过引入组合模式,Sunny公司设计的杀毒软件具有良好的可扩展性,在增加新的文件类型时,无须修改现有类库代码,只需增加一个新的文件类作为AbstractFile类的子类即可,但是由于在AbstractFile中声明了大量用于管理和访问成员构件的方法,例如add()、remove()等方法,我们不得不在新增的文件类中实现这些方法,提供对应的错误提示和异常处理。为了简化代码,我们有以下两个解决方案:

解决方案一:将叶子构件的add()、remove()等方法的实现代码移至AbstractFile类中,由AbstractFile提供统一的默认实现,代码如下所示:

[java] view plain copy
  1. //提供默认实现的抽象构件类
  2. abstract class AbstractFile {
  3. public void add(AbstractFile file) {
  4. System.out.println("对不起,不支持该方法!");
  5. }
  6. public void remove(AbstractFile file) {
  7. System.out.println("对不起,不支持该方法!");
  8. }
  9. public AbstractFile getChild(int i) {
  10. System.out.println("对不起,不支持该方法!");
  11. return null;
  12. }
  13. public abstract void killVirus();
  14. }

如果客户端代码针对抽象类AbstractFile编程,在调用文件对象的这些方法时将出现错误提示。如果不希望出现任何错误提示,我们可以在客户端定义文件对象时不使用抽象层,而直接使用具体叶子构件本身,客户端代码片段如下所示:

[java] view plain copy
  1. class Client {
  2. public static void main(String args[]) {
  3. //不能透明处理叶子构件
  4. ImageFile file1,file2;
  5. TextFile file3,file4;
  6. VideoFile file5;
  7. AbstractFile folder1,folder2,folder3,folder4;
  8. //其他代码省略
  9. }
  10. }

这样就产生了一种不透明的使用方式,即在客户端不能全部针对抽象构件类编程,需要使用具体叶子构件类型来定义叶子对象。

解决方案二:除此之外,还有一种解决方法是在抽象构件AbstractFile中不声明任何用于访问和管理成员构件的方法,代码如下所示:

[java] view plain copy
  1. abstract class AbstractFile {
  2. public abstract void killVirus();
  3. }

此时,由于在AbstractFile中没有声明add()、remove()等访问和管理成员的方法,其叶子构件子类无须提供实现;而且无论客户端如何定义叶子构件对象都无法调用到这些方法,不需要做任何错误和异常处理,容器构件再根据需要增加访问和管理成员的方法,但这时候也存在一个问题:客户端不得不使用容器类本身来声明容器构件对象,否则无法访问其中新增的add()、remove()等方法,如果客户端一致性地对待叶子和容器,将会导致容器构件的新增对客户端不可见,客户端代码对于容器构件无法再使用抽象构件来定义,客户端代码片段如下所示:

[java] view plain copy
  1. class Client {
  2. public static void main(String args[]) {
  3. AbstractFile file1,file2,file3,file4,file5;
  4. Folder folder1,folder2,folder3,folder4; //不能透明处理容器构件
  5. //其他代码省略
  6. }
  7. }

在使用组合模式时,根据抽象构件类的定义形式,我们可将组合模式分为透明组合模式和安全组合模式两种形式:

(1) 透明组合模式

透明组合模式中,抽象构件Component中声明了所有用于管理成员对象的方法,包括add()、remove()以及getChild()等方法,这样做的好处是确保所有的构件类都有相同的接口。在客户端看来,叶子对象与容器对象所提供的方法是一致的,客户端可以相同地对待所有的对象。透明组合模式也是组合模式的标准形式,虽然上面的解决方案一在客户端可以有不透明的实现方法,但是由于在抽象构件中包含add()、remove()等方法,因此它还是透明组合模式,透明组合模式的完整结构如图11-6所示:

图11-6  透明组合模式结构图

透明组合模式的缺点是不够安全,因为叶子对象和容器对象在本质上是有区别的。叶子对象不可能有下一个层次的对象,即不可能包含成员对象,因此为其提供add()、remove()以及getChild()等方法是没有意义的,这在编译阶段不会出错,但在运行阶段如果调用这些方法可能会出错(如果没有提供相应的错误处理代码)。

(2) 安全组合模式

安全组合模式中,在抽象构件Component中没有声明任何用于管理成员对象的方法,而是在Composite类中声明并实现这些方法。这种做法是安全的,因为根本不向叶子对象提供这些管理成员对象的方法,对于叶子对象,客户端不可能调用到这些方法,这就是解决方案二所采用的实现方式。安全组合模式的结构如图11-7所示:

图11-7  安全组合模式结构图

安全组合模式的缺点是不够透明,因为叶子构件和容器构件具有不同的方法,且容器构件中那些用于管理成员对象的方法没有在抽象构件类中定义,因此客户端不能完全针对抽象编程,必须有区别地对待叶子构件和容器构件。在实际应用中,安全组合模式的使用频率也非常高,在Java AWT中使用的组合模式就是安全组合模式。

组合模式的安全模式与透明模式相关推荐

  1. 教程篇(5.4) 14. 透明模式 ❀ FortiGate 安全 ❀ Fortinet 网络安全专家 NSE 4

    在这节课中你将学习如何在一个FortiGate里做透明模式和二层交换. 完成这节课程之后,你应该具备配置FortiGate作为二层交换来使用的实用技能,它们包括: 配置FortiGate接口作为二层交 ...

  2. 【高级篇 / HA】(6.0) ❀ 07. HA 下的透明模式 ❀ FortiGate 防火墙

    [简介]虽然NAT模式使用场景比较多,但是有时也会用到透明模式.在HA下使用透明模式,与单机模式下使用透明模式会略有不同,我们看看HA使用透明模式会发生什么.   转换成透明模式 透明模式在Web界面 ...

  3. 【接口篇 / Lan】(5.6) ❀ 03. 透明模式下的链路聚合连接 ❀ FortiGate 防火墙

    [简介]我们已经知道,在透明模式下,防火墙的接口都是没有IP地址的,那么他们还可以建立链路聚合吗?   网络拓扑 在某些企业,由于内网比较复杂,新加入的防火墙不希望对内网进行任何改动,因此可以选项将防 ...

  4. 在linux下配置网桥透明模式防火墙

    在linux下配置网桥透明模式防火墙 一.透明模式防火墙与透明代理的概念       一般而言,防火墙的两个网络接口应分属两个不同的网络,根据系统管理员定义的访问规则在两个接口之间转发数据包,或者拒绝 ...

  5. 防火墙工作在哪个层_Stratix 5950工业防火墙透明模式使用

    工业防火墙为工业网络安全中必不可少的部分,工业控制的二层网络的安全,Stratix5950工业防火墙提供了Transparent(透明)工作模式. 透明模式介绍 1.透明模式:透明模式的工业防火墙,接 ...

  6. php 组合模式,php设计模式(十三)透明组合模式

    组合模式用来解决整体和部分可以一致对待的问题: 比如说 文件夹 和其下的 文件: 可以复制文件也可以复制整个文件夹: 组合模式是将对象组合成树形结构以表示整体和部分的层次结构: 可以方便的增加节点: ...

  7. 7、大话设计模式--状态模式 、适配器模式、备忘录模式、组合模式、迭代器模式

    第十六章:无尽加班何时休--状态模式 状态模式 :   优点: 缺点: 所使用的项目是:工作状态 功能: 界面: 设计思路: 收获: 附: 1.概述 在软件开发过程中,应用程序可能会根据不同的情况作出 ...

  8. 设计模式GOF23之-------------------结构型模式(适配器模式、代理模式、桥接模式、装饰模式、组合模式、外观模式、享元模式)

    一 结构型模式 二 适配器模式 下面我将用代码模拟键盘usb接口和ps/2的转接器 的适配器过程: 首先定义客户需求: package GOF23;public interface Target {v ...

  9. 设计模式之结构型模式:适配器模式、桥接模式、组合模式、装饰器模式、代理模式、

    文章目录 什么是结构型模式 适配模式 适配器的数据结构 适配器的实现 缺省适配器 适配器优缺点 适配器模式的使用环境 桥接模式 桥接模式数据结构 桥接模式的实现 桥接模式和适配器模式的联用 桥接模式的 ...

最新文章

  1. Maven settings.xml配置详解
  2. 动态规划算法的优化技巧
  3. 格罗方德起诉台积电侵犯16项专利、影响巨大;中兴通讯与印尼Smartfren展开合作;网传FB开发新通讯应用Threads……...
  4. html中两个图片叠放,CSS实现图片叠放(勾选图标)
  5. C++|Java工作笔记-google protobuf基本使用
  6. 范例 在 Setting 里加入 HiApk Settings 选项
  7. 计算机辅助管理与制造,计算机辅助设计与制造,对产品的设备进行管理,完成产品加工制造...
  8. android settheme不起作用,android-主题,样式和别名嵌套不起作用
  9. Houdini工程文件合集
  10. Sonic一站式开源分布式集群云真机测试平台阶段性使用总结
  11. vector扩容时以2倍或1.5倍扩容的原因
  12. IDEA右键菜单管理--懒人专用
  13. jest中的mock,jest.fn()、jest.spyOn()、jest.mock()
  14. 不知道是真是假的流量购买---有待考察
  15. 201912月全国计算机二级考试,201912月天津计算机二级报名时间:12月5日-12月7日!附报名入口...
  16. ViewPager嵌套ViewPager,内层ViewPager
  17. 常见手机的useragent
  18. 丢手绢 【约瑟夫环】
  19. Python 10个优雅的写法,你会吗?
  20. 面经02-深信服面试

热门文章

  1. 高等数学下-赵立军-北京大学出版社-题解-练习8.5
  2. B-树、B+树、B*树详解
  3. 操作系统内存管理--简单、页式、段式、段页式
  4. 【NOI2016】优秀的拆分【后缀数组】【ST表】【关键点】【调和级数复杂度】【差分】
  5. 【CF1194E】Count The Rectangles【类扫描线】【单调性】【树状数组】
  6. Educational Codeforces Round 111 (Rated for Div. 2)
  7. gym 102875A -- Array(未更新完)
  8. AT1983-[AGC001E]BBQ Hard【dp,组合数学】
  9. P3265-[JLOI2015]装备购买【线性基,拟阵贪心】
  10. jzoj4017-逃跑【0/1分数规划,线段树,dp】