Java设计模式之组合模式详解

文章目录

      • 详解Java设计模式之组合模式
        • 案例引入
        • 组合模式
          • 定义
          • 模式类图结构
            • 相关角色
            • 典型代码
          • 案例分析
            • 类图设计
            • 实例代码
            • 结果分析
          • JavaJDK中的组合模式
          • 透明组合模式
          • 安全组合模式
          • 组合模式优点
          • 组合模式缺点
          • 组合模式适用环境

详解Java设计模式之组合模式

案例引入
  • Windows的操作系统目录结构如下

    Java设计模式之组合模式详解_第1张图片

  • 分析

    • 在树形目录结构中,包含文件和文件夹两类不同的元素
      • 在文件家中可以继续包含子文件夹
      • 在文件中不能在包含子文件(word中嵌入图片不是一个概念
    • 文件夹也叫作容器(Container)节点
    • 文件也叫作叶子(Leaf)节点
    • 当容器对象的某一个方法被调用时,将遍历整个属性结构,寻找包含这个方法的成员对象并调用执行,牵一而动百,其中使用了递归的机制来对整个结构进行处理
    • 由于容器节点和叶子结点在功能上的区别,在使用这些对象的代码中必须有区别的对象容器节点和叶子节点,而实际上大多数情况下客户端希望一致的处理他们,因为对于这些对象的区别对待会导致程序较为复杂(就比如说需要进行不断的判定结构)

如何一致性的对待容器对象和叶子对象呢?????再比如一个大果盘里面装有小果盘和果子,小果盘里又装着小小果盘和果子,们想要吃到所有的水果的过程也是类似的。由此我们正式引出组合模式

组合模式
定义

组合模式:组合多个对象形成树形结构表示具有整体和部分关系的层次结构。组合模式让客户端可以统一的对待单个对象和组合对象。

Composite Pattern:Compose objects into tree structures to represent part-whole hierarchies. Composite lets clients treat individual objects and composition of objects uniformly.

  • 组合模式属于对象结构性模式
  • 又称为"部分-整体"模式
  • 将对象组织到树形结构中,可以用来描述整体和部分的关系。
模式类图结构

Java设计模式之组合模式详解_第2张图片

相关角色
  • Component 抽象构件
  • Leaf 叶子构件
  • Composite 容器构件
典型代码
  • 抽象构件Component

    • public abstract class Component {
          public abstract void add(Component c); //增加成员
          public abstract void remove(Component c); //删除成员
          public abstract Component getChild(int i); //获取成员
          public abstract void operation();  //业务方法
      }
      
      
  • 叶子构件 Leaf

    • public class Leaf extends Component {
          public void add(Component c) { 
              //异常处理或错误提示
          }	
      		
          public void remove(Component c) { 
              //异常处理或错误提示
          }
      	
          public Component getChild(int i) { 
              //异常处理或错误提示
              return null; 
          }
      	
          public void operation() {
              //叶子构件具体业务方法的实现
          } 
      
      
  • 容器构件

    • public class Composite extends Component {
          private ArrayList<Component> list = new ArrayList<Component>();
      	
          public void add(Component c) {
              list.add(c);
          }
      	
          public void remove(Component c) {
              list.remove(c);
          }
      	
          public Component getChild(int i) {
              return (Component)list.get(i);
          }
      	
          public void operation() {
              //容器构件具体业务方法的实现,将递归调用成员构件的业务方法
              for(Object obj:list) {
                  ((Component)obj).operation();
              }
          } 	
      }
      
案例分析

某软件公司欲开发一个杀毒(Antivirus)软件,该软件既可以对某个文件夹(Folder)杀毒,也可以对某个指定的文件(File)进行杀毒。该杀毒软件还可以根据各类文件的特点,为不同类型的文件提供不同的杀毒方式,例如图像文件(ImageFile)和文本文件(TextFile)的杀毒方式就有所差异。
现使用组合模式来设计该杀毒软件的整体框架。

类图设计

Java设计模式之组合模式详解_第3张图片

实例代码

(1) AbstractFile:抽象文件类,充当抽象构件类
(2) ImageFile:图像文件类,充当叶子构件类
(3) TextFile:文本文件类,充当叶子构件类
(4) VideoFile:视频文件类,充当叶子构件类
(5) Folder:文件夹类,充当容器构件类
(6) Client:客户端测试类

具体代码和更多相关实验可见我的gitee

https://gitee.com/plushuang/HelloWord/tree/master/src/csu/edu/cn/designpattern/compositepattern/example

结果分析

见代码

  • 如果需要更换操作节点,例如只对文件夹“文本文件”进行杀毒,客户端代码只需修改一行即可
  • 在具体实现时,可以创建图形化界面让用户来选择所需操作的根节点,无须修改源代码,符合开闭原则
JavaJDK中的组合模式

Java设计模式之组合模式详解_第4张图片

透明组合模式

其实也就是在抽象构件中提供add、remove、get等方法,但是这些方法叶子节点是不能使用的,只有容器节点能够使用。不够安全,一旦叶子节点调用需要进行报错或者提示处理,但是能够让客户端一致性的对待两者

Java设计模式之组合模式详解_第5张图片

安全组合模式

也就是抽象构件中不含上述三种方法,能够保证安全性,但是导致的就是不够透明,客户端不能完全的针对抽象编程。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-6YQOsnst-1640067963922)(C:\Users\PlusHuang\AppData\Roaming\Typora\typora-user-images\image-20211221142113986.png)]

组合模式优点
  • 可以清楚地定义分层次的复杂对象,表示对象的全部或部分层次,让客户端忽略了层次的差异,方便对整个层次结构进行控制
  • 客户端可以一致地使用一个组合结构或其中单个对象,不必关心处理的是单个对象还是整个组合结构,简化了客户端代码
  • 增加新的容器构件和叶子构件都很方便,符合开闭原则
  • 为树形结构的面向对象实现提供了一种灵活的解决方案
组合模式缺点
  • 在增加新构件时很难对容器中的构件类型进行限制
组合模式适用环境
  • 在具有整体和部分的层次结构中,希望通过一种方式忽略整体与部分的差异,客户端可以一致地对待它们
  • 在一个使用面向对象语言开发的系统中需要处理一个树形结构
  • 在一个系统中能够分离出叶子对象和容器对象,而且它们的类型不固定,需要增加一些新的类型

你可能感兴趣的:(设计模式,组合模式,java,开发语言,设计模式)