结构性设计模式之Composite(组合)
摘要:
Composite(组合)模式通过树形结构表示"部分-整体"层次关系,使得用户能够统一处理单个对象和组合对象。该模式包含Component(组件接口)、Leaf(叶子节点)和Composite(组合节点)三个核心角色,适用于需要表示对象层次结构并统一操作的场景。示例代码展示了文件夹结构的实现,Folder类管理子组件,File类作为叶子节点,通过递归遍历实现统一处理。该模式简化了客户端代码,使系统更易扩展和维护。
1)意图;
将对象组合成树型结构以表示“部分-整体”的层次结构。Composite使得用户对单个对象和组合对象的使用具有一致性。
2)结构
其中:
-
Componect 为组合中的对象声明接口:在适当情况下实现所有类共有接口的默认行为:
声明一个接口用户访问和管理 Componect的子组件;(可选)在递归结构中定义一个
接口,用于访问一个父组件,并在合适的情况下实现它。
-
Leaf 在组合中表示叶节点对象,叶结点没有子节点节点;在组合中定义图元对象的行为。
-
Composite定义有子组件的那些组件的行为;存储子组件;在Component接口中实现与子组件有关的操作。
-
Client 通过 Component 接口操纵组合组件的对象。
3)适用性
Composite 模式下适用于:
- 想表示对象的部分-整体层次结构。
- 希望用户忽略组合对象与单个对象的不同,用户将统一地使用组合结构中的所有对象。
代码
import java.util.ArrayList;
import java.util.List;
/**
* @author psd 结构性设计模式之组合设计模式
*/
public class ComponentDemo {
public static void main(String[] args) {
AbstractFile root = new Folder("root");
AbstractFile folderA = new Folder("folderA");
AbstractFile folderB = new Folder("folderB");
AbstractFile fileC = new File("fileC");
AbstractFile fileD = new File("fileD");
AbstractFile fileE = new File("fileE");
root.add(folderA);
root.add(folderB);
root.add(fileC);
folderA.add(fileD);
folderA.add(fileE);
print(root);
}
private static void print(AbstractFile file) {
file.printName();
List<AbstractFile> childrenList = file.getChildren();
if (childrenList == null) {
return;
}
for (AbstractFile children : childrenList) {
print(children);
}
}
}
abstract class AbstractFile {
protected String name;
public void printName() {
System.out.println(name);
}
public abstract boolean add(AbstractFile file);
public abstract boolean remove(AbstractFile file);
public abstract List<AbstractFile> getChildren();
}
/**
* 文件夹
*/
class Folder extends AbstractFile {
public Folder(String name) {
this.name = name;
}
List<AbstractFile> children = new ArrayList<>();
@Override
public boolean add(AbstractFile file) {
return children.add(file);
}
@Override
public boolean remove(AbstractFile file) {
return children.remove(file);
}
@Override
public List<AbstractFile> getChildren() {
return children;
}
}
class File extends AbstractFile {
public File(String name) {
this.name = name;
}
@Override
public boolean add(AbstractFile file) {
return false;
}
@Override
public boolean remove(AbstractFile file) {
return false;
}
@Override
public List<AbstractFile> getChildren() {
return null;
}
}
代码目录结构如下:
欢我的文章记得点个在看,或者点赞,持续更新中ing…