一天一个设计模式——Composite组合模式
一、模式说明
能够使容器与内容物具有一致性,创造出递归结构的模式就是Composite组合模式。
举个例子:计算机中的文件系统中有文件和文件夹的概念,我们知道,文件夹可以包含文件,也可以包含子文件夹,子文件夹中又可以包含文件和文件夹。如果将文件和文件夹都看作“目录条目(Directory Entry)”,那么文件系统就形成了一个递归的容器,这就是一种组合模式。
更多例子,在Windows操作系统中,一个窗口中可以包含子窗口,从而形成容器的递归;一条宏命令又可以包含另一个宏命令;一个文章章节又可以包含多个子章节。。。这种具有树状结构的数据都适用于组合模式。
二、模式类图

三、代码示例
在示例程序中,我们创建一个Entry目录条目类,并让File文件类和Dictory文件夹类去继承它。
1、FileTreatementException类
package com.designpattern.cn.Entry;
public class FileTreatementException extends RuntimeException {
public FileTreatementException(){
}
public FileTreatementException(String msg){
super(msg);
}
}
2、Entry条目类
package com.designpattern.cn.Entry;
public abstract class Entry {
public abstract String getName();
public abstract int getSize();
public Entry add(Entry entry) throws FileTreatementException{
throw new FileTreatementException();
}
public void PrintList(){
printList("");
}
protected abstract void printList(String prefix);
public String toString(){
return getName() + " (" + getSize() + ")";
}
}
3、File文件类
package com.designpattern.cn.Entry;
public class File extends Entry {
private String name;
private int size;
public File(String name, int size){
this.name = name;
this.size = size;
}
public String getName(){
return name;
}
public int getSize(){
return size;
}
protected void printList(String prefix){
System.out.println(prefix + "/" + this);
}
}
4、Directory目录类
package com.designpattern.cn.Entry; import java.util.ArrayList;
import java.util.Iterator; public class Directory extends Entry {
private String name;
private ArrayList directory = new ArrayList();
public Directory(String name){
this.name = name;
}
public String getName(){
return name;
}
public int getSize(){
int size = 0;
Iterator it = directory.iterator();
while (it.hasNext()){
Entry entry = (Entry) it.next();
size += entry.getSize();
}
return size;
}
public Entry add(Entry entry){
directory.add(entry);
return this;
}
protected void printList(String prefix){
System.out.println(prefix + "/" + this);
Iterator it = directory.iterator();
while (it.hasNext()){
Entry entry = (Entry) it.next();
entry.printList(prefix + "/" + name);
}
}
}
5、Main方法类和运行结果
package com.designpattern.cn.Entry;
public class Main {
public static void main(String[] args) {
try {
System.out.println("Making root entries...");
Directory rootdir = new Directory("root");
Directory bindir = new Directory("bin");
Directory tmpdir = new Directory("tmp");
Directory usrdir = new Directory("usr");
rootdir.add(bindir);
rootdir.add(tmpdir);
rootdir.add(usrdir);
bindir.add(new File("vi", 10000));
bindir.add(new File("latex", 20000));
rootdir.printList("");
}catch (FileTreatementException e){
e.printStackTrace();
}
}
}

四、模式中的角色
- Leaf树叶角色:该角色中不能再放入其他对象,如示例中的File类;
- Composite复合物类:在其中可以放入Leaf和Composite复合物,如示例程序中的Directory类;
- Component类:使Leaf和Composite角色具有一致性的角色,如示例中的Entry类;
- Client客户角色:使用复合模式的对象。
五、相关的设计模式
- Command模式:Command模式编写宏命令时会使用Composite模式;
- Vistor访问者模式:可以使用访问者模式访问Composite中的递归结构;
- Decorator装饰者模式:Composite模式通过Component角色使Composite和Leaf具有一致性,Decorator模式使装饰框和内容具有一致性;
一天一个设计模式——Composite组合模式的更多相关文章
- C++设计模式-Composite组合模式
Composite组合模式作用:将对象组合成树形结构以表示“部分-整体”的层次结构.Composite使得用户对单个对象和组合对象的使用具有一致性. UML图如下: 在Component中声明所有用来 ...
- [C++设计模式] composite 组合模式
组合(Composite)模式的其他翻译名称也非常多,比方合成模式.树模式等等.在<设计模式>一书中给出的定义是:将对象以树形结构组织起来,以达成"部分-总体"的层次结 ...
- C#设计模式(10)——组合模式(Composite Pattern)
一.引言 在软件开发过程中,我们经常会遇到处理简单对象和复合对象的情况,例如对操作系统中目录的处理就是这样的一个例子,因为目录可以包括单独的文件,也可以包括文件夹,文件夹又是由文件组成的,由于简单对象 ...
- 乐在其中设计模式(C#) - 组合模式(Composite Pattern)
原文:乐在其中设计模式(C#) - 组合模式(Composite Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 组合模式(Composite Pattern) 作者:weba ...
- C#设计模式(10)——组合模式(Composite Pattern)(转)
一.引言 在软件开发过程中,我们经常会遇到处理简单对象和复合对象的情况,例如对操作系统中目录的处理就是这样的一个例子,因为目录可以包括单独的文件,也可以包括文件夹,文件夹又是由文件组成的,由于简单对象 ...
- 设计模式08: Composite 组合模式(结构型模式)
Composite 组合模式(结构型模式) 对象容器的问题在面向对象系统中,我们常会遇到一类具有“容器”特征的对象——即他们在充当对象的同时,又是其他对象的容器. public interface I ...
- C#设计模式:组合模式(Composite Pattern)
一,C#设计模式:组合模式(Composite Pattern) using System; using System.Collections.Generic; using System.Linq; ...
- JavaScript设计模式之----组合模式
javascript设计模式之组合模式 介绍 组合模式是一种专门为创建Web上的动态用户界面而量身制定的模式.使用这种模式可以用一条命令在多个对象上激发复杂的或递归的行为.这可以简化粘合性代码,使其更 ...
- 十一、Composite 组合模式
原理: 代码清单 Entity public abstract class Entry { public abstract String getName(); public abstract int ...
随机推荐
- ffmpeg 学习: 003-关键函数介绍
背景 了解一些关键函数对于开发的帮助比较大. avformat_open_input FFMPEG 打开媒体的过程开始于 avformat_open_input,因此该函数的重要性不可忽视. 在该函数 ...
- 使用six库将Python2的项目完全转移到python3
SIX是用于python2与python3兼容的库. 它存在的目的是为了拥有无需修改即可在Python 2和Python 3上同时工作的代码.话虽这么说,但是这并不代表在Python 3中引用该库就可 ...
- 求第K大数(分治)
题意:已知N个数,求第K大数. 分析: 1.复杂度O(n). 2.利用快排中划分的原理,每次划分以序列中第一个数x为标准,将序列划分为{比x大的数}x{比x小的数}. 3.若集合{比x大的数}中元素为 ...
- Day7 - A - Visible Lattice Points POJ - 3090
A lattice point (x, y) in the first quadrant (x and y are integers greater than or equal to 0), othe ...
- 015、MySQL取今天是第几季度,往后几个月是第几季度
#取今天是第几季度 SELECT QUARTER( curdate( ) ); #取往后几个月是第几季度 , INTERVAL MONTH ) ); , INTERVAL MONTH ) ); , I ...
- Quartz 调用
讲解 在线Cron表达式 调用(DLL下载) static void Main(string[] args) { //1.任务调度调用 //开启任务,操作数据,然后将数据广播给指定用户 //Cron表 ...
- webservice调试(XML参数)
<![CDATA[ <?xml version="1.0" encoding="UTF-8"?><MsgText> <use ...
- HDU - 6198 number number number(规律+矩阵快速幂)
题意:已知F0 = 0,F1 = 1,Fn = Fn - 1 + Fn - 2(n >= 2), 且若n=Fa1+Fa2+...+Fak where 0≤a1≤a2≤⋯≤a,n为正数,则n为mj ...
- idea下maven项目下spring junit 测试用例
使用idea在编写的类下右键Go->Test或者ctrl+shift+t,点击create new test会在相应目录下创建test类 别写代码如下 @RunWith(value = Spri ...
- Django——优美的Path()函数
path( )作用:解析URL地址 path( ) 标准语法: (<>为必须的参数,[]为可选参数) path(<route>, <view>, [name=Non ...