设计模式之组合模式(Java实现)

Composite(组合)

一、意图

将对象组合成树型结构以表示“部分-整体”的层次结构。Composite使得用户对单个对象和组合对象的使用具有一致性。

二、结构

组合模式的结构如图7.33所示。 其中: • Component为组合中的对象声明接口;在适当情况下实现所有类共有接口的默认行为; 声明一个接口用于访问和管理Component的子组件;(可选)在递归结构中定义一个接口,用于访问一个父组件,并在合适的情况下实现它。 • Leaf在组合中表示叶结点对象,叶结点没有子结点;在组合中定义图元对象的行为。 • Composite定义有子组件的那些组件的行为;存储子组件;在Component接口中实现与子组件有关的操作。 • Client通过Component接口操纵组合组件的对象。

三、适用性

Composite模式适用于: • 想表示对象的部分-整体层次结构。 • 希望用户忽略组合对象与单个对象的不同,用户将统一地使用组合结构中的所有对象。

四、实现

现欲构造一文件/目录树,采用组合(Composite)设计模式来设计,得到的类图如下图 所示: 首先 创建抽象文件类。

abstract class AbstractFile {
          
   
	protected String name;  //文件或目录名称
	public void printName() {
          
   
		System.out.println(name);	
	}
	//给一个目录增加子目录或文件
	public abstract boolean addChild(AbstractFile file);
	//删除一个目录的子目录或文件
	public abstract boolean removeChild(AbstractFile file);
	//获得一个目录的子目录或文件
	public abstract List<AbstractFile> getChildren();
}

然后 创建文件类和文件夹类分别继承抽象文件类。

class File extends AbstractFile {
          
   
	public File(String name) {
          
   
		this.name = name;
	}
	public boolean addChild(AbstractFile file) {
          
    
		return false;
	}
	public boolean removeChild(AbstractFile file) {
          
    
		return false;
	}
	public List<AbstractFile> getChildren() {
          
    
		return null ;
	}
}

class Folder extends AbstractFile {
          
   
	private List<AbstractFile> childList;  //存储子目录或文件
	public Folder(String name) {
          
   
		this.name = name;
		this.childList = new ArrayList<AbstractFile>();
	}
	public boolean addChild(AbstractFile file) {
          
   
		return childList.add(file);
	}
	public boolean removeChild(AbstractFile file) {
          
   
		return childList.remove(file);
	}
	public List <AbstractFile> getChildren() {
          
    
		return childList ; 
	}
}

最后 测试一下。

public class Composite {
          
   

	public static void main(String[] args) {
          
   
		// TODO Auto-generated method stub
		// 创造一个树形的文件/目录结构
		AbstractFile rootFolder = new Folder("c:\");
		AbstractFile compositeFolder = new Folder("composite");
		AbstractFile windowsFolder = new Folder("windows");
		AbstractFile file = new File("TestComposite.java");
		rootFolder.addChild(compositeFolder);
		rootFolder.addChild(windowsFolder);
		compositeFolder.addChild(file);
		// 打印目录文件数
		printTree(rootFolder);
		}
		private static void printTree(AbstractFile ifile) {
          
   
		ifile.printName();
		List<AbstractFile> children = ifile.getChildren();
		if (children == null) return;
		for (AbstractFile file : children) {
          
   
			printTree(file) ;
		}
	}

}

运行结果:

经验分享 程序员 微信小程序 职场和发展