Appearance
组合模式
定义
组合模式(Composite Pattern),将对象组合成树形结构以表示“部分-整体”的层次结构。组合模式使得用户对单个对象和组合对象的使用具有一致性。
优点
- 组合模式使得客户端代码可以一致地处理单个对象和组合对象,无需关心自己处理的是单个对象还是组合对象,可以递归地使用组合结构。
- 组合模式可以清楚地定义分层次的复杂对象,表示对象的全部或部分层次,它让客户端忽略了层次的差异,方便对整个层次结构进行操作。
缺点
- 使得设计更加复杂。客户端需要花更多时间理清类之间的层次关系。
- 使得增加新部件变得困难。如果在组合模式中增加新的部件,则需要抽象出新的部件类,并且可能在每一层中都要实现该类,这违背了“开闭原则”。
使用场景
- 表示对象的部分-整体层次结构。
- 从一个整体中能够独立出部分模块或功能。
代码实现
java
public interface Node {
String name();
boolean hasChild();
void addNode(Node child);
void removeNode(Node child);
void print();
}
java
public class BattleNode implements Node{
private String name;
public BattleNode(String name) {
this.name = name;
}
@Override
public String name() {
return this.name;
}
@Override
public boolean hasChild() {
return false;
}
public void setName(String name) {
this.name = name;
}
@Override
public void addNode(Node child) {
}
@Override
public void removeNode(Node child) {
}
@Override
public void print() {
System.out.println(this.name);
}
}
java
public class SupplyNode implements Node{
private String name;
private final List<Node> children = new ArrayList<>();
public SupplyNode(String name) {
this.name = name;
}
@Override
public String name() {
return this.name;
}
@Override
public void addNode(Node child){
children.add(child);
}
@Override
public void removeNode(Node child){
children.remove(child);
}
public List<Node> getChildren() {
return this.children;
}
public void setName(String name) {
this.name = name;
}
@Override
public boolean hasChild() {
return true;
}
@Override
public void print() {
System.out.println(this.name);
for (Node node : children) {
node.print();
}
}
}
java
public class Client {
public static void main(String[] args) {
Node root = new SupplyNode("创世节点");
Node s1 = new SupplyNode("阿卡拉城");
Node s2 = new SupplyNode("暴风城");
Node s3 = new SupplyNode("黄金城");
Node s4 = new SupplyNode("河阳城");
Node s5 = new SupplyNode("铁炉堡");
Node s6 = new SupplyNode("斯坦索姆");
Node s7 = new SupplyNode("奥金顿");
Node s8 = new SupplyNode("达纳苏斯");
Node b1 = new BattleNode("迷雾丛林");
Node b2 = new BattleNode("暴风沼泽");
Node b3 = new BattleNode("猛毒丛林");
Node b4 = new BattleNode("海盗湾");
Node b5 = new BattleNode("荆棘谷");
root.addNode(s1);
root.addNode(s2);
s1.addNode(s3);
s2.addNode(s4);
s2.addNode(s5);
s2.addNode(s6);
s3.addNode(s7);
s3.addNode(s8);
s2.addNode(b1);
s2.addNode(b2);
s2.addNode(b3);
s3.addNode(b4);
s3.addNode(b5);
root.print();
}
}