zoukankan      html  css  js  c++  java
  • 组合模式

      组合模式允许你将对象组合成树形结构来表现“整体部分”层次结构,组合能让用户以一致的方式来处理个别对象和组合对象。

      以菜单为例,因为子菜单的存在,所以当遍历菜单时,会遇到个别对象(菜单项)和对象组合(子菜单)。

      还好有组合模式。。。

      现在创建一个组件接口来作为菜单和菜单项的共同接口,让我们能够用统一的做法来处理菜单和菜单项。换句话说,我们可以针对菜单和菜单项调用相同的方法。。。But,菜单组件好像扮演了两个角色,是的,确实扮演了两个角色,Y?

      组合模式以单一责任设计原则换取透明性。通过让组件的接口同时包含一些管理子节点和叶节点的操作,客户就可以将组合和叶节点一视同仁。也就是说,一个元素究竟是叶节点还是组合,对客户是透明的。

      因为最好能够为这些方法提供默认的实现,so。。。抽象类的干活。。。

      代码示例:

    public abstract class MenuComponent
    {
        public void Add (MenuComponent menuComponent)
        {
            throw new Exception();
        }
    
        public void Remove(MenuComponent menuComponent)
        {
            throw new Exception();
        }
    
        public string getName()
        {
            throw new Exception();
        }
    
        public boolean IsVeg ()
        {
            throw new Exception();
        }
    
        public void print()
        {
            throw new Exception();
        }
    }

      因为有些方法只对菜单项有意义,另一些方法只对菜单有意义,默认实现是抛出异常,这样,若菜单(项)不支持某个方法,直接继承默认实现就OK了。

      下面实现菜单项的类,该类只要实现对它有意义的方法即可:

    public class MenuItem extends MenuComponent
    {
        string name;
        boolean veg;
    
        public MenuItem(string name, boolean veg)
        {
            this.name = name;
            this.veg = veg;
        }
    
        public string getName()
        {
            return name;
        }
    
        public boolean IsVeg()
        {
            return veg;
        }
    
        public void print()
        {
            system.out.print("this is " + getName());
        }
    }

      下面实现菜单的类,同样,该类只要实现对它有意义的方法即可:

    public class Menu extends MenuComponent
    {
        string name;
        ArrayList menuComponents = new ArrayList();
    
        public Menu(string name)
        {
            this.name = name;
        }
    
        public string getName()
        {
            return name;
        }
    
        public void Add(MenuComponent menuComponent)
        {
            menuComponents.add(menuComponent);
        }
    
        public void Remove(MenuComponent menuComponent)
        {
            menuComponents.remove(menuComponent);
        }
    
        public void print()
        {
            system.out.print("this is " + getName() + "菜单,包含:");
    
            // 该部分采用了迭代器模式
            Iterator iterator = menuComponents.iterator();   
            while(iterator.hasNext())
            {
                MenuComponent menuComponent = (MenuComponent) iterator.next();
                menuComponent.print()     // 递归
            }
        }
    }

    。。。。。。

      这样我们可以使用menuComponent来处理菜单和菜单项了,而不必去理会该对象是菜单项(个别对象)还是菜单(组合对象)。。。

  • 相关阅读:
    100个经典的动态规划方程
    poj 2105 IP Address
    codeforces 299 A. Ksusha and Array
    codeforces 305 C. Ivan and Powers of Two
    性能测试实战 | 修改 JMeter 源码,定制化聚合压测报告
    Pytest 测试框架训练营,测试大咖带你搞定自动化+接口测试实战 | 限时免费报名
    MTSC 测试开开发大会(深圳站),报名立减 100 元!
    测试人面试 BAT 大厂之前,需要做好哪些准备?
    iOS 自动化测试踩坑(二):Appium 架构原理、环境命令、定位方式
    【北京】美团打车招聘职位
  • 原文地址:https://www.cnblogs.com/hachun/p/3625304.html
Copyright © 2011-2022 走看看