定义
组合模式,允许你将对象组合成树形结构来表现“整体/部分”层次结构。组合能让客户以一致的方式处理个别对象以及对象组合。
实例
继续以餐厅和煎饼屋合并的例子为例。
前面说到,餐厅菜单用ArrayList实现,煎饼屋菜单用数组,合并后两个都不想改变自己的实现,那么我们通过迭代器模式,统一了这两种实现,完成菜单遍历功能。
现在,餐厅需要在菜单上加个小菜单,甜品菜单。它包含在餐厅菜单里,所以无法用迭代器模式完成。那么,试试组合模式。将甜品菜单看做是组件,组合到餐厅菜单中。
餐厅菜单和甜品菜单都继承MenuComponent抽象类,即菜单组件:
public abstract class MenuComponent {
public void add(MenuComponent menuComponent) {
}
public void remove(MenuComponent menuComponent) {
}
public MenuComponent getChild(int i) {
}
public String getName() {
}
public void print() {
}
}
实现菜单项,这是组合类图里的叶类,它实现组合内元素的行为。代码如下:
public class MenuItem extends MenuComponent {
String name;
public MenuItem(String name) {
this.name = name;
}
public String getName() {
return name;
}
public void print() {
System.out.println(" " + getName());
}
}
实现组合菜单,此组合类可以持有菜单项或其它菜单。代码如下:
public class Menu extends MenuComponent {
ArrayList menuComponents = new ArrayList();
String name;
public Menu(String name) {
this.name = name;
}
public void add(MenuComponent menuComponent) {
menuComponents.add(menuComponent);
}
public void remoce(MenuComponent menuComponent) {
menuComponents.remove(menuComponent);
}
public MenuComponent getChild(int i) {
return (MenuComponent)menuComponents.get(i);
}
public String getName() {
return name;
}
public void print() {
System.out.println("\n" + getName());
// 通过迭代器遍历所有菜单组件。
// 遍历过程中,可能遇到其它菜单,或者是遇到菜单项。
// 如果遇到另一个菜单对象,它的print()方法会开始另一个遍历,依次类推。
// 由于菜单和菜单项都实现了print(),那我们只要调用print()即可。
Iterator iterator = menuComponents.iterator();
while(iterator.hasNext()) {
MenuComponent menuComponent = (MenuComponent)iterator.next();
menuComponent.print();
}
}
}
小结
-
组合模式提供一个结构,可同时包容个别对象和组合对象。
-
组合模式允许客户对个人对象以及组合对象一视同仁。
-
组合结构内的任意对象称为组件,组件可以是组合,也可以是叶节点。
-
在实现组合模式时,有许多设计上的折中。你要根据需要平衡透明性和安全性。
发表评论