刘文涛

Pattern,UML,Struts2,Hibernate3,Spring2,Oracle,mysql,weblogic,tomcat,compass,lucene,nutch,sitemesh,freemarker,div,css,ExtJs,Flex,seo

   :: 首页 ::  ::  ::  :: 管理 ::

2010年3月1日 #

状态模式(state pattern)和策略模式(strategy pattern)的实现方法非常类似,都是利用多态把一些操作分配到一组相关的简单的类中,因此很多人认为这两种模式实际上是相同的。然而

  • 在现实世界中,策略(如促销一种商品的策略)和状态(如同一个按钮来控制一个电梯的状态,又如手机界面中一个按钮来控制手机)是两种完全不同的思想。当我们对状态和策略进行建模时,这种差异会导致完全不同的问题。例如,对状态进行建模时,状态迁移是一个核心内容;然而,在选择策略时,迁移与此毫无关系。另外,策略模式允许一个客户选择或提供一种策略,而这种思想在状态模式中完全没有。
  • 一个策略是一个计划或方案,通过执行这个计划或方案,我们可以在给定的输入条件下达到一个特定的目标。策略是一组方案,他们可以相互替换;选择一个策略,获得策略的输出。策略模式用于随不同外部环境采取不同行为的场合。我们可以参考微软企业库底层Object Builder的创建对象的strategy实现方式。
  • 而状态模式不同,对一个状态特别重要的对象,通过状态机来建模一个对象的状态;状态模式处理的核心问题是状态的迁移,因为在对象存在很多状态情况下,对各个business flow,各个状态之间跳转和迁移过程都是及其复杂的。例如一个工作流,审批一个文件,存在新建、提交、已修改、HR部门审批中、老板审批中、HR审批失败、老板审批失败等状态,涉及多个角色交互,涉及很多事件,这种情况下用状态模式(状态机)来建模更加合适;把各个状态和相应的实现步骤封装成一组简单的继承自一个接口或抽象类的类,通过另外的一个Context来操作他们之间的自动状态变换,通过event来自动实现各个状态之间的跳转。在整个生命周期中存在一个状态的迁移曲线,这个迁移曲线对客户是透明的。我们可以参考微软最新的WWF 状态机工作流实现思想。
  • 在状态模式中,状态的变迁是由对象的内部条件决定,外界只需关心其接口,不必关心其状态对象的创建和转化;而策略模式里,采取何种策略由外部条件(C)决定。
posted @ 2010-03-01 17:45 刘文涛| 编辑 收藏

2010年2月25日 #

7、PROTOTYPE

原型模式 : 

posted @ 2010-02-25 19:29 刘文涛| 编辑 收藏

6、BUILDER

建造模式 : 将产品的内部表象和产品的生产过程 分割开来 。








posted @ 2010-02-25 19:28 刘文涛| 编辑 收藏

5、multiton

多例模式 
(1) 有上限多例模式





/**
 * User: liuwentao@wentao365.com
 * Date: 2008-12-6 Time: 11:45:33
 * 
<p/>
 * note: 有上限多实例类模式
 *       骰子
 */
public class Die {

    private static Die die1 = new Die();
    private static Die die2 = new Die();

    /**
     * 私有构造函数保证 外界 无法直接将此类实例化
     */
    private Die() {

    }

    /**
     * 工厂方法
     * @param i
     * @return
     */
    public static Die getInstance(int i) {
        switch (i) {
            case 0:
                return die1;
            case 1:
                return die2;
            default:
                return null;
        }
    }

    /**
     * 掷骰子 返回 1-6 之间的随机数
     * @return int
     */
    public synchronized int dice() {
        System.out.println("-----------------------------");
        Date date = new Date();
        Random random = new Random(date.getTime());
        //random.nextInt()可能返回 负数
        int value = Math.abs(random.nextInt())%6 + 1;
        return value;
    }
}


/**
 * User: liuwentao@wentao365.com
 * Date: 2008-12-6 Time: 11:55:01
 * 
<p/>
 * note: 测试 有上限 多实例模式 (Multiton)
 */
public class DieTest extends TestCase {

    public void testMain(){
        Die die1 = Die.getInstance(0);
        Die die2 = Die.getInstance(1);
        System.out.println(die1.dice());
        System.out.println(die2.dice());
    }
}


(2) 无上限多例模式


posted @ 2010-02-25 19:27 刘文涛| 编辑 收藏

4、SINGLETON

单例模式 : 
(1) Eager 饿汉模式 : 仅适用于 Java  ; 



public class EagerSingleton {
    //类被加载时,静态变量就被初始化
    private static EagerSingleton ourInstance = new EagerSingleton();

    /**
     * 外界只能通过此方法获得自身的实例
     * @return SingletonDemo
     */
    public static EagerSingleton getInstance() {
        return ourInstance;
    }

    /**
     * 构造函数对外不可见
     * 单例模式最显著的特点
     */
    private EagerSingleton() {
    }
}

(2) Lazy 懒汉模式 : 适用于Java,C++ (因为static 代码块的执行顺序c++不固定,java是固定的,在构造方法之前)



public class LazySingleton {
    //类被加载时,静态变量不会被初始化
    private static LazySingleton lazySingleton = null;

    /**
     * 默认构造函数 是 private
     * 防止外界调用,同时此类也不能被继承
     */
    private LazySingleton(){

    }

    /**
     * synchronized :同步化
     * @return
     */
    synchronized public static LazySingleton getInstance(){
        if(lazySingleton == null){
            lazySingleton = new LazySingleton();
        }
        return lazySingleton;
    }
}

posted @ 2010-02-25 19:26 刘文涛| 编辑 收藏

2、FACTORY METHOD

工厂方法模式 (也叫 PlyMorphic Factory : 多态性工厂模式)




posted @ 2010-02-25 19:25 刘文涛| 编辑 收藏

3、Abastract Factory

抽象工厂模式 :每个具体工厂 负责多个具体产品的生产






posted @ 2010-02-25 19:25 刘文涛| 编辑 收藏

1、Simple Factory : 

简单工厂模式 ( 也叫 : Static Factory Method : 静态工厂方法模式)



    /**
     * 静态工厂方法
     * @param fruitName
     * @return  Fruit
     * @throws factory.simplefactory.exception.NoFruitException
     */
    public static Fruit getFruit(String fruitName) throws NoFruitException {
        //根据客户端的请求 创建出 不同的水果 对象实例
        if (fruitName.equalsIgnoreCase("apple")) {
            return new Apple();
        } else if (fruitName.equalsIgnoreCase("strawberry")) {
            return new Strawberry();
        } else if (fruitName.equalsIgnoreCase("grape")) {
            return new Grape();
        } else {
            throw new NoFruitException("no this fruit for your request");  //错误的请求
       }
    }
 
posted @ 2010-02-25 19:24 刘文涛| 编辑 收藏

8、BRIDGE

桥梁模式:将抽象化与实现化脱耦,使得二者可以独立的变化。

桥梁模式很好的体现了 "开-闭“ 原则 (OCP)   以及 ”组合/聚合复用原则“ (CARP)

一个不好的设计 :


使用桥梁模式的设计 : 





八戒投胎的故事 : 

假设 : 



有了上面的假设 我们 用 桥梁模式 完美 设计  : 



肉体和灵魂  本来有  继承关系 。

但为了 让 灵魂和 肉体 各自 演化 ,  设计成桥梁模式 ,在 灵魂 中 有一个 对肉体的 引用。 

如 飞机那个例子 : 

abstract public class Airplane {
    protected AirplaneMaker airplaneMaker;
    
    abstract public void fly() ;
}

飞机抽象类 有 一个 对 飞机生产厂 的 引用。 飞机上飞机厂造的,所以飞机里有对飞机厂的引用,肉体上灵魂托生的 所以肉体里有对灵魂的引用,颜料是用毛笔表现出来的 所以 颜料里有对毛笔的引用。

这里假设 是 飞机生产厂(AirplaneMaker) 和 飞机(Airplane) 有一种 继承关系 (难理解怎么会有这种关系,但假设有。)


蜡笔与燃料的例子


小时候我们都用蜡笔画画,一盒蜡笔12种颜色。一开始我都是用最小号的蜡笔画个太阳公公、月亮婆婆足够了。后来开始画一些抽象派的作品,就得换中号的了,要不然画个背景都要描半天,好一盒中号的也是12种颜色。再后来我开始转向豪放派,中号就有些捉襟见肘了,只好换大号的了,好一盒大号的也只有12种颜色。你看,像我这样不太出名的画家就需要36种画笔,哇,太麻烦了。但是据我观察,另一些比我出名的画家倒是没有这么多笔,他们只有几把刷子和一些颜料,这样就解决了蜡笔的“种类爆炸”问题。”






桥梁模式:将抽象化与实现化脱耦,使得二者可以独立的变化,也就是说将他们之间的强关联变成弱关联,也就是指在一个软件系统的抽象化和实现化之间使用组合/聚合关系而不是继承关系,从而使两者可以独立的变化。

posted @ 2010-02-25 19:21 刘文涛| 编辑 收藏

6、PROXY

代理模式 :

给某一个对象提供一个代理对象,并由代理对象控制对原对象的引用。














posted @ 2010-02-25 19:20 刘文涛| 编辑 收藏

仅列出标题  下一页