这篇文章距离最后更新已过15 天,如果文章内容或图片资源失效,请留言反馈,我会及时处理,谢谢!
定义
- 将对象组合成树形结构来表示“部分 - 整体”的层次结构。
- 组合结构使得用户对单个对象和组合对象的使用保持一致性。
- 整体 和 部分 可以 一致对待 的问题
使用场景
- 部分、整体场景
- 文件夹管理
- 公司分公司部门统一管理OA
代码实现
abstract class Component
{
protected string name;
public Component(string name)
{
this.name = name;
}
public abstract void Add(Component c);
public abstract void Remove(Component c);
public abstract void Display(int depth);
}
class Leaf: Component
{
public Leaf(string name):base(name){ }
public override void Add(Component c)
{
Console.WriteLine("Cannot add to leaf");
}
public override void Remove(Component c)
{
Console.WriteLine("Cannot remove from a leaf");
}
public override void Display(int depth)
{
Console.WriteLine(new string('-', depth) + name);
}
}
class Composite: Component
{
private List<Component> children = new List<Component>();
public Composite(string name):base(name) { }
public override void Add(Component c)
{
children.Add(c);
}
public override void Remove(Component c)
{
children.Remove(c);
}
public override void Display(int depth)
{
Console.WriteLine(new string('-', depth) + name);
foreach(Component component in children)
{
component.Display(depth + 2);
}
}
}
void Main()
{
Composite root = new Composite("root");
root.Add(new Leaf("Leaf A"));
root.Add(new Leaf("Leaf B"));
Composite comp = new Composite("Comp X");
comp.Add(new Leaf("Leaf XA"));
comp.Add(new Leaf("Leaf XB"));
Composite comp1 = new Composite("Comp XY");
var leaf = new Leaf("Leaf XYA");
comp1.Add(leaf);
comp1.Remove(leaf);
comp.Add(comp1);
root.Add(comp);
root.Display(1);
}
透明模式 与 安全模式
- 透明模式是 枝节点 和 叶节点 都存在 Add 和 Remove 方法,而叶节点不需要实现这两个方法
- 安全模式是 不在Component 中声明 Add 和 Remove 方法,而放到枝节点中,这样叶节点就不用实现 Add 和 Remove 方法,但是由于不够透明,客户端调用需要做相应的判断
优点
- 高层模块调用简单,节点可以自由添加
- 组合模式使得客户端代码可以一致地处理单个对象和组合对象,无须关心自己处理的是单个对象,还是组合对象,这简化了客户端代码
缺点
- 叶节点类和枝节点类都是实现类而不是接口类,违反了依赖倒置原则
- 不容易用继承的方法来增加构件的新功能
- 不容易限制容器中的构件
- 设计较复杂,客户端需要花更多时间理清类之间的层次关系