HeadFirst设计模式之组合模式

一、

1.The Composite Pattern allows us to build structures of objects in the form of trees that contain both compositions of objects and individual objects as nodes.

2.Using a composite structure,we can apply the same operations over both composites and individual objects. In other words, in most cases we can ignore the differences between compositions of objects and individual objects.

3.The Composite Pattern allows you to compose objects into tree structures to represent part-whole hierarchies. Composite

lets clients treat individual objects and compositions of objects uniformly.

4

.

5.

6.

7.

8.

9.

二、

1.

 1 package headfirst.designpatterns.composite.menu;
 2
 3 public abstract class MenuComponent {
 4
 5     public void add(MenuComponent menuComponent) {
 6         throw new UnsupportedOperationException();
 7     }
 8     public void remove(MenuComponent menuComponent) {
 9         throw new UnsupportedOperationException();
10     }
11     public MenuComponent getChild(int i) {
12         throw new UnsupportedOperationException();
13     }
14
15     public String getName() {
16         throw new UnsupportedOperationException();
17     }
18     public String getDescription() {
19         throw new UnsupportedOperationException();
20     }
21     public double getPrice() {
22         throw new UnsupportedOperationException();
23     }
24     public boolean isVegetarian() {
25         throw new UnsupportedOperationException();
26     }
27
28     public void print() {
29         throw new UnsupportedOperationException();
30     }
31 }

2.

 1 package headfirst.designpatterns.composite.menu;
 2
 3 import java.util.Iterator;
 4 import java.util.ArrayList;
 5
 6 public class Menu extends MenuComponent {
 7     ArrayList<MenuComponent> menuComponents = new ArrayList<MenuComponent>();
 8     String name;
 9     String description;
10
11     public Menu(String name, String description) {
12         this.name = name;
13         this.description = description;
14     }
15
16     public void add(MenuComponent menuComponent) {
17         menuComponents.add(menuComponent);
18     }
19
20     public void remove(MenuComponent menuComponent) {
21         menuComponents.remove(menuComponent);
22     }
23
24     public MenuComponent getChild(int i) {
25         return (MenuComponent)menuComponents.get(i);
26     }
27
28     public String getName() {
29         return name;
30     }
31
32     public String getDescription() {
33         return description;
34     }
35
36     public void print() {
37         System.out.print("\n" + getName());
38         System.out.println(", " + getDescription());
39         System.out.println("---------------------");
40
41         Iterator<MenuComponent> iterator = menuComponents.iterator();
42         while (iterator.hasNext()) {
43             MenuComponent menuComponent =
44                 (MenuComponent)iterator.next();
45             menuComponent.print();
46         }
47     }
48 }

3.

 1 package headfirst.designpatterns.composite.menu;
 2
 3 public class MenuItem extends MenuComponent {
 4     String name;
 5     String description;
 6     boolean vegetarian;
 7     double price;
 8
 9     public MenuItem(String name,
10                     String description,
11                     boolean vegetarian,
12                     double price)
13     {
14         this.name = name;
15         this.description = description;
16         this.vegetarian = vegetarian;
17         this.price = price;
18     }
19
20     public String getName() {
21         return name;
22     }
23
24     public String getDescription() {
25         return description;
26     }
27
28     public double getPrice() {
29         return price;
30     }
31
32     public boolean isVegetarian() {
33         return vegetarian;
34     }
35
36     public void print() {
37         System.out.print("  " + getName());
38         if (isVegetarian()) {
39             System.out.print("(v)");
40         }
41         System.out.println(", " + getPrice());
42         System.out.println("     -- " + getDescription());
43     }
44 }

4.

 1 package headfirst.designpatterns.composite.menu;
 2
 3 public class Waitress {
 4     MenuComponent allMenus;
 5
 6     public Waitress(MenuComponent allMenus) {
 7         this.allMenus = allMenus;
 8     }
 9
10     public void printMenu() {
11         allMenus.print();
12     }
13 }

5.

  1 package headfirst.designpatterns.composite.menu;
  2
  3 public class MenuTestDrive {
  4     public static void main(String args[]) {
  5         MenuComponent pancakeHouseMenu =
  6             new Menu("PANCAKE HOUSE MENU", "Breakfast");
  7         MenuComponent dinerMenu =
  8             new Menu("DINER MENU", "Lunch");
  9         MenuComponent cafeMenu =
 10             new Menu("CAFE MENU", "Dinner");
 11         MenuComponent dessertMenu =
 12             new Menu("DESSERT MENU", "Dessert of course!");
 13         MenuComponent coffeeMenu = new Menu("COFFEE MENU", "Stuff to go with your afternoon coffee");
 14
 15         MenuComponent allMenus = new Menu("ALL MENUS", "All menus combined");
 16
 17         allMenus.add(pancakeHouseMenu);
 18         allMenus.add(dinerMenu);
 19         allMenus.add(cafeMenu);
 20
 21         pancakeHouseMenu.add(new MenuItem(
 22             "K&B‘s Pancake Breakfast",
 23             "Pancakes with scrambled eggs, and toast",
 24             true,
 25             2.99));
 26         pancakeHouseMenu.add(new MenuItem(
 27             "Regular Pancake Breakfast",
 28             "Pancakes with fried eggs, sausage",
 29             false,
 30             2.99));
 31         pancakeHouseMenu.add(new MenuItem(
 32             "Blueberry Pancakes",
 33             "Pancakes made with fresh blueberries, and blueberry syrup",
 34             true,
 35             3.49));
 36         pancakeHouseMenu.add(new MenuItem(
 37             "Waffles",
 38             "Waffles, with your choice of blueberries or strawberries",
 39             true,
 40             3.59));
 41
 42         dinerMenu.add(new MenuItem(
 43             "Vegetarian BLT",
 44             "(Fakin‘) Bacon with lettuce & tomato on whole wheat",
 45             true,
 46             2.99));
 47         dinerMenu.add(new MenuItem(
 48             "BLT",
 49             "Bacon with lettuce & tomato on whole wheat",
 50             false,
 51             2.99));
 52         dinerMenu.add(new MenuItem(
 53             "Soup of the day",
 54             "A bowl of the soup of the day, with a side of potato salad",
 55             false,
 56             3.29));
 57         dinerMenu.add(new MenuItem(
 58             "Hotdog",
 59             "A hot dog, with saurkraut, relish, onions, topped with cheese",
 60             false,
 61             3.05));
 62         dinerMenu.add(new MenuItem(
 63             "Steamed Veggies and Brown Rice",
 64             "Steamed vegetables over brown rice",
 65             true,
 66             3.99));
 67
 68         dinerMenu.add(new MenuItem(
 69             "Pasta",
 70             "Spaghetti with Marinara Sauce, and a slice of sourdough bread",
 71             true,
 72             3.89));
 73
 74         dinerMenu.add(dessertMenu);
 75
 76         dessertMenu.add(new MenuItem(
 77             "Apple Pie",
 78             "Apple pie with a flakey crust, topped with vanilla icecream",
 79             true,
 80             1.59));
 81
 82         dessertMenu.add(new MenuItem(
 83             "Cheesecake",
 84             "Creamy New York cheesecake, with a chocolate graham crust",
 85             true,
 86             1.99));
 87         dessertMenu.add(new MenuItem(
 88             "Sorbet",
 89             "A scoop of raspberry and a scoop of lime",
 90             true,
 91             1.89));
 92
 93         cafeMenu.add(new MenuItem(
 94             "Veggie Burger and Air Fries",
 95             "Veggie burger on a whole wheat bun, lettuce, tomato, and fries",
 96             true,
 97             3.99));
 98         cafeMenu.add(new MenuItem(
 99             "Soup of the day",
100             "A cup of the soup of the day, with a side salad",
101             false,
102             3.69));
103         cafeMenu.add(new MenuItem(
104             "Burrito",
105             "A large burrito, with whole pinto beans, salsa, guacamole",
106             true,
107             4.29));
108
109         cafeMenu.add(coffeeMenu);
110
111         coffeeMenu.add(new MenuItem(
112             "Coffee Cake",
113             "Crumbly cake topped with cinnamon and walnuts",
114             true,
115             1.59));
116         coffeeMenu.add(new MenuItem(
117             "Bagel",
118             "Flavors include sesame, poppyseed, cinnamon raisin, pumpkin",
119             false,
120             0.69));
121         coffeeMenu.add(new MenuItem(
122             "Biscotti",
123             "Three almond or hazelnut biscotti cookies",
124             true,
125             0.89));
126
127         Waitress waitress = new Waitress(allMenus);
128
129         waitress.printMenu();
130     }
131 }

三、带Iterator

1.

 1 package headfirst.designpatterns.composite.menuiterator;
 2
 3 import java.util.*;
 4
 5 public abstract class MenuComponent {
 6
 7     public void add(MenuComponent menuComponent) {
 8         throw new UnsupportedOperationException();
 9     }
10     public void remove(MenuComponent menuComponent) {
11         throw new UnsupportedOperationException();
12     }
13     public MenuComponent getChild(int i) {
14         throw new UnsupportedOperationException();
15     }
16
17     public String getName() {
18         throw new UnsupportedOperationException();
19     }
20     public String getDescription() {
21         throw new UnsupportedOperationException();
22     }
23     public double getPrice() {
24         throw new UnsupportedOperationException();
25     }
26     public boolean isVegetarian() {
27         throw new UnsupportedOperationException();
28     }
29
30     public abstract Iterator<MenuComponent> createIterator();
31
32     public void print() {
33         throw new UnsupportedOperationException();
34     }
35 }

2.

 1 package headfirst.designpatterns.composite.menuiterator;
 2
 3 import java.util.*;
 4
 5 public class CompositeIterator implements Iterator<MenuComponent> {
 6     Stack<Iterator<MenuComponent>> stack = new Stack<Iterator<MenuComponent>>();
 7
 8     public CompositeIterator(Iterator<MenuComponent> iterator) {
 9         stack.push(iterator);
10     }
11
12     public MenuComponent next() {
13         if (hasNext()) {
14             Iterator<MenuComponent> iterator = stack.peek();
15             MenuComponent component = iterator.next();
16             stack.push(component.createIterator());
17             return component;
18         } else {
19             return null;
20         }
21     }
22
23     public boolean hasNext() {
24         if (stack.empty()) {
25             return false;
26         } else {
27             Iterator<MenuComponent> iterator = stack.peek();
28             if (!iterator.hasNext()) {
29                 stack.pop();
30                 return hasNext();
31             } else {
32                 return true;
33             }
34         }
35     }
36
37     /*
38      * No longer needed as of Java 8
39      *
40      * (non-Javadoc)
41      * @see java.util.Iterator#remove()
42      *
43     public void remove() {
44         throw new UnsupportedOperationException();
45     }
46     */
47 }

3.

 1 package headfirst.designpatterns.composite.menuiterator;
 2
 3 import java.util.Iterator;
 4
 5 public class NullIterator implements Iterator<MenuComponent> {
 6
 7     public MenuComponent next() {
 8         return null;
 9     }
10
11     public boolean hasNext() {
12         return false;
13     }
14
15     /*
16      * No longer needed as of Java 8
17      *
18      * (non-Javadoc)
19      * @see java.util.Iterator#remove()
20      *
21     public void remove() {
22         throw new UnsupportedOperationException();
23     }
24     */
25 }

4.

 1 package headfirst.designpatterns.composite.menuiterator;
 2
 3 import java.util.Iterator;
 4 import java.util.ArrayList;
 5
 6 public class Menu extends MenuComponent {
 7     Iterator<MenuComponent> iterator = null;
 8     ArrayList<MenuComponent> menuComponents = new ArrayList<MenuComponent>();
 9     String name;
10     String description;
11
12     public Menu(String name, String description) {
13         this.name = name;
14         this.description = description;
15     }
16
17     public void add(MenuComponent menuComponent) {
18         menuComponents.add(menuComponent);
19     }
20
21     public void remove(MenuComponent menuComponent) {
22         menuComponents.remove(menuComponent);
23     }
24
25     public MenuComponent getChild(int i) {
26         return menuComponents.get(i);
27     }
28
29     public String getName() {
30         return name;
31     }
32
33     public String getDescription() {
34         return description;
35     }
36
37
38     public Iterator<MenuComponent> createIterator() {
39         if (iterator == null) {
40             iterator = new CompositeIterator(menuComponents.iterator());
41         }
42         return iterator;
43     }
44
45
46     public void print() {
47         System.out.print("\n" + getName());
48         System.out.println(", " + getDescription());
49         System.out.println("---------------------");
50
51         Iterator<MenuComponent> iterator = menuComponents.iterator();
52         while (iterator.hasNext()) {
53             MenuComponent menuComponent = iterator.next();
54             menuComponent.print();
55         }
56     }
57 }

5.

 1 package headfirst.designpatterns.composite.menuiterator;
 2
 3 import java.util.Iterator;
 4
 5 public class MenuItem extends MenuComponent {
 6
 7     String name;
 8     String description;
 9     boolean vegetarian;
10     double price;
11
12     public MenuItem(String name,
13                     String description,
14                     boolean vegetarian,
15                     double price)
16     {
17         this.name = name;
18         this.description = description;
19         this.vegetarian = vegetarian;
20         this.price = price;
21     }
22
23     public String getName() {
24         return name;
25     }
26
27     public String getDescription() {
28         return description;
29     }
30
31     public double getPrice() {
32         return price;
33     }
34
35     public boolean isVegetarian() {
36         return vegetarian;
37     }
38
39     public Iterator<MenuComponent> createIterator() {
40         return new NullIterator();
41     }
42
43     public void print() {
44         System.out.print("  " + getName());
45         if (isVegetarian()) {
46             System.out.print("(v)");
47         }
48         System.out.println(", " + getPrice());
49         System.out.println("     -- " + getDescription());
50     }
51
52 }

6.

 1 package headfirst.designpatterns.composite.menuiterator;
 2
 3 import java.util.Iterator;
 4
 5 public class Waitress {
 6     MenuComponent allMenus;
 7
 8     public Waitress(MenuComponent allMenus) {
 9         this.allMenus = allMenus;
10     }
11
12     public void printMenu() {
13         allMenus.print();
14     }
15
16     public void printVegetarianMenu() {
17         Iterator<MenuComponent> iterator = allMenus.createIterator();
18
19         System.out.println("\nVEGETARIAN MENU\n----");
20         while (iterator.hasNext()) {
21             MenuComponent menuComponent = iterator.next();
22             try {
23                 if (menuComponent.isVegetarian()) {
24                     menuComponent.print();
25                 }
26             } catch (UnsupportedOperationException e) {}
27         }
28     }
29 }

7.

  1 package headfirst.designpatterns.composite.menuiterator;
  2
  3 public class MenuTestDrive {
  4     public static void main(String args[]) {
  5
  6         MenuComponent pancakeHouseMenu =
  7             new Menu("PANCAKE HOUSE MENU", "Breakfast");
  8         MenuComponent dinerMenu =
  9             new Menu("DINER MENU", "Lunch");
 10         MenuComponent cafeMenu =
 11             new Menu("CAFE MENU", "Dinner");
 12         MenuComponent dessertMenu =
 13             new Menu("DESSERT MENU", "Dessert of course!");
 14
 15         MenuComponent allMenus = new Menu("ALL MENUS", "All menus combined");
 16
 17         allMenus.add(pancakeHouseMenu);
 18         allMenus.add(dinerMenu);
 19         allMenus.add(cafeMenu);
 20
 21         pancakeHouseMenu.add(new MenuItem(
 22             "K&B‘s Pancake Breakfast",
 23             "Pancakes with scrambled eggs, and toast",
 24             true,
 25             2.99));
 26         pancakeHouseMenu.add(new MenuItem(
 27             "Regular Pancake Breakfast",
 28             "Pancakes with fried eggs, sausage",
 29             false,
 30             2.99));
 31         pancakeHouseMenu.add(new MenuItem(
 32             "Blueberry Pancakes",
 33             "Pancakes made with fresh blueberries, and blueberry syrup",
 34             true,
 35             3.49));
 36         pancakeHouseMenu.add(new MenuItem(
 37             "Waffles",
 38             "Waffles, with your choice of blueberries or strawberries",
 39             true,
 40             3.59));
 41
 42         dinerMenu.add(new MenuItem(
 43             "Vegetarian BLT",
 44             "(Fakin‘) Bacon with lettuce & tomato on whole wheat",
 45             true,
 46             2.99));
 47         dinerMenu.add(new MenuItem(
 48             "BLT",
 49             "Bacon with lettuce & tomato on whole wheat",
 50             false,
 51             2.99));
 52         dinerMenu.add(new MenuItem(
 53             "Soup of the day",
 54             "A bowl of the soup of the day, with a side of potato salad",
 55             false,
 56             3.29));
 57         dinerMenu.add(new MenuItem(
 58             "Hotdog",
 59             "A hot dog, with saurkraut, relish, onions, topped with cheese",
 60             false,
 61             3.05));
 62         dinerMenu.add(new MenuItem(
 63             "Steamed Veggies and Brown Rice",
 64             "A medly of steamed vegetables over brown rice",
 65             true,
 66             3.99));
 67
 68         dinerMenu.add(new MenuItem(
 69             "Pasta",
 70             "Spaghetti with Marinara Sauce, and a slice of sourdough bread",
 71             true,
 72             3.89));
 73
 74         dinerMenu.add(dessertMenu);
 75
 76         dessertMenu.add(new MenuItem(
 77             "Apple Pie",
 78             "Apple pie with a flakey crust, topped with vanilla icecream",
 79             true,
 80             1.59));
 81         dessertMenu.add(new MenuItem(
 82             "Cheesecake",
 83             "Creamy New York cheesecake, with a chocolate graham crust",
 84             true,
 85             1.99));
 86         dessertMenu.add(new MenuItem(
 87             "Sorbet",
 88             "A scoop of raspberry and a scoop of lime",
 89             true,
 90             1.89));
 91
 92         cafeMenu.add(new MenuItem(
 93             "Veggie Burger and Air Fries",
 94             "Veggie burger on a whole wheat bun, lettuce, tomato, and fries",
 95             true,
 96             3.99));
 97         cafeMenu.add(new MenuItem(
 98             "Soup of the day",
 99             "A cup of the soup of the day, with a side salad",
100             false,
101             3.69));
102         cafeMenu.add(new MenuItem(
103             "Burrito",
104             "A large burrito, with whole pinto beans, salsa, guacamole",
105             true,
106             4.29));
107
108         Waitress waitress = new Waitress(allMenus);
109
110         waitress.printVegetarianMenu();
111
112     }
113 }
时间: 2024-10-12 04:13:50

HeadFirst设计模式之组合模式的相关文章

设计模式之组合模式

当需求中是体现部分与整体层次的结构时,以及你希望忽略组合对象与单个对象的不同,统一的使用组合结构中的所有对象时,就应该考虑使用组合模式了.例如:我们单个复制一个文件和多个复制文件,对我们而言,并不在乎一个文件的复制与多个文件复制的区别,也就是我们的操作是一样的. 下面的代码是建立一个公司的组织结构,其中各个部分,不管是分公司还是部门,都拥有一套相同的功能操作. 代码如下: using System; using System.Collections.Generic; using System.L

设计模式之组合模式(Composite)摘录

23种GOF设计模式一般分为三大类:创建型模式.结构型模式.行为模式. 创建型模式抽象了实例化过程,它们帮助一个系统独立于如何创建.组合和表示它的那些对象.一个类创建型模式使用继承改变被实例化的类,而一个对象创建型模式将实例化委托给另一个对象.创建型模式有两个不断出现的主旋律.第一,它们都将关于该系统使用哪些具体的类的信息封装起来.第二,它们隐藏了这些类的实例是如何被创建和放在一起的.整个系统关于这些对象所知道的是由抽象类所定义的接口.因此,创建型模式在什么被创建,谁创建它,它是怎样被创建的,以

HeadFirst 设计模式 04 工厂模式

除了 new 操作符之外, 还有更多创造对象的方法. 工厂处理创建对象的细节. 这么做的目的是为了抽象, 例如把创建比萨的代码包装进一个类, 当以后实现改变时, 只需修改这个类即可. 利用静态方法定义一个简单的工厂, 这是很常见的技巧, 被称作静态工厂. 所有工厂模式斗都用来封装对象的创建, javascript 也是一样. 工厂方法模式通过让子类决定该创建的对象是什么, 来达到将对象创建的过程封装的目的. 工厂模式定义了一个创建对象的接口, 但由子类决定要实例化的类是哪一个. 工厂方法让类把实

设计模式之组合模式(Composite)

1.定义 组合模式(Composite Pattern)也叫合成模式,将对象组合成树形结构以表示"整体-部分"的层次结构,使得用户对单个对象和组合对象的使用具有一致性. 2.通用类图 Component抽象构件角色:定义参加组合对象的共有方法和属性,可以定义一些默认的行为或属性. Leaf叶子构件:叶子对象,其下再也没有其他的分支,也就是遍历的最小单位. Composite树枝构件:树枝对象,它的作用是组合树枝节点和叶子节点形成一个树形结构. 3.通用源代码 package Compo

c++设计模式15 --组合模式

今天研究了一下设计模式15 组合模式 本人是菜鸟一枚,所以一开始完全不懂组合究竟是什么意思.先上图一张,树形结构图: 文档说,如果想做出这样的结构,通常考虑组合模式.那是为什么呢?现在让我们看一下组合模式的类图一本结构 想了很久,结合源代码,才搞明白,其实这个组合,意思就是说,如果我们要做这种树状结果,比如公司想让我们吧所有部门人员的 姓名,职位,薪水遍历出来,这个时候怎么办呢?那我们看树状机构图,有叶子结点和枝干结点,2种,但是2种有共性,那就是每个结点都有姓名,职位,薪水.所有叶子结点和枝干

【C++实现】HeadFirst设计模式之策略模式

策略模式定义了算法家族,分别封装起来,让它们之间可以相互替换,此模式让算法的变化独立于使用算法的客户. Head First设计模式中介绍策略模式时以Duck类作为例子,其中用flyBehavior和quackBehavior两个接口引用变量代表鸭子飞行和鸭子叫这两种行为,通过改变flyBehavior和quackBehavior来满足不同的Duck子类的不同行为,这样带来的好处就是可以在运行时改变Duck子类的行为.下面是我用C++改写的代码. //MyDuckMain.cpp #includ

C#设计模式:组合模式(Composite Pattern)

一,C#设计模式:组合模式(Composite Pattern) using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; namespace _9.组合模式 { //组合模式主要用来处理一类具有"容器特征"的对象--即它们在充当对象的同时,又可以作为容器包含其他多个对象. //组合模式,将对象组合成树形结构以表示

C#设计模式(10)——组合模式(Composite Pattern)

一.引言 在软件开发过程中,我们经常会遇到处理简单对象和复合对象的情况,例如对操作系统中目录的处理就是这样的一个例子,因为目录可以包括单独的文件,也可以包括文件夹,文件夹又是由文件组成的,由于简单对象和复合对象在功能上区别,导致在操作过程中必须区分简单对象和复合对象,这样就会导致客户调用带来不必要的麻烦,然而作为客户,它们希望能够始终一致地对待简单对象和复合对象.然而组合模式就是解决这样的问题.下面让我们看看组合模式是怎样解决这个问题的. 二.组合模式的详细介绍 2.1 组合模式的定义 组合模式

每天一个设计模式之组合模式

作者按:<每天一个设计模式>旨在初步领会设计模式的精髓,目前采用javascript和python两种语言实现.诚然,每种设计模式都有多种实现方式,但此小册只记录最直截了当的实现方式 :) 原文地址是:<每天一个设计模式之组合模式> 欢迎关注个人技术博客:godbmw.com.每周 1 篇原创技术分享!开源教程(webpack.设计模式).面试刷题(偏前端).知识整理(每周零碎),欢迎长期关注! 如果您也想进行知识整理 + 搭建功能完善/设计简约/快速启动的个人博客,请直接戳the