设计模式之装饰模式

来源:互联网 发布:厂家销售软件 编辑:程序博客网 时间:2024/06/05 16:58

装饰模式概念

装饰模式动态的为对象增加新的功能,提供了比继承更具有弹性的解决方案。

装饰模式类图

Component是一个抽象的类或者接口,具体的类实现抽象类的某些功能,但是如果需要对具体的类附加一些新增的功能的时候,就需要Decorator类出马了。

下面的例子是受HeaDFirst一书启迪:

有一家蛋糕店,蛋糕店的计费系统设计如下:

Cake{

    public abstract cost();

    // 计算当前蛋糕的价格

}


蛋糕会因为工艺流程不同而收取不同的费用,比如海绵蛋糕(CakeA),泡芙蛋糕(CakeB),戚风蛋糕等等(CakeC),需要的人工时间不一样,导致收费不一致,所以分别采取不同的类来实现,我们可以定义不同的子类继承自Cake类,然后实现不同的cost计费方法,这样可以简单的解决这个问题,但是随着市场的不断演进,蛋糕设计技术也不段发展,渐渐涌现除了很多不同口味的蛋糕,水果蛋糕,芝士蛋糕,抹茶蛋糕,冰激凌蛋糕,鲜奶蛋糕等等,随着添加成分的不同,蛋糕形成了种类繁多的集合。这个时候如果每种蛋糕都使用继承的方式去实现计费方式的话,就会产生庞大的类群,使得程序不易维护。


这个时候就需要装饰模式来解决这种问题了,我们可以定义装饰者Decorator继承自Cake,并且实现了cost方法,如果我们添加的成分不一样,比如Fruit,Milk,Cheese。。。

class CakeA extends Cake{

    private int cost(){

        return 10;

    }

}

public abstract class Decorator extends Cake {

    private abstract int cost();

}


class FruitDecorator{

    private int priceFruit;

    private Cake mCake;

    public FruitDecorator(Cake cake) {

        mCake = cake;

    }

    private int cost(){

        return priceFruit + mCake.cost() ;

    }

}


class MilkDecorator{

   private int priceMilk;

   private Cake mCake;

    public MilkDecorator(Cake cake) {

        mCake = cake;

    }

    private int cost(){

        return priceMilk+ mCake.cost() ;

    }
}

其余可按照示例代码类似实现,这样客户如果想要水果鲜奶海绵蛋糕的话,代码可以如下实现:

class Client{

    public static void main(String[] args){

        Cake cakeA= new CakeA();

        Cake fruitDecorator = new FruitDecorator(cakeA);

        Cake milkDecorator= new MilkDecorator(fruitDecorator);

        int price = milkDecorator.cost();

    }

}

备注:

装饰者和被装饰者具有相同的超类型;

可以用一个或者多个装饰者包装一个对象;

由于装饰者和被装饰者具有相同的超类型,所以可以在任何需要使用被装饰对象的地方使用装饰者对象来代替;

装饰者可以在所委托被装饰者的行为之前或者之后加上自己的行为,已达到特定的目的;

对象可以在任何时候动态的被装饰。

Android中装饰模式举例

感觉和装饰模式还是有点差别的,等后续遇到装饰模式的例子在拿来用吧!


装饰模式优缺点

优点:

1 装饰模式没有继承带来的数量庞大的类,使得代码易于维护,更具有灵活性。

2 可以为现有的类动态的添加附加功能。

缺点:

1 会引入大量的小类,导致代码阅读者不易了解到装饰模式的设计方式;

2 如果把代码携程依赖与具体组件类型,那么装饰者就会出问题,只有针对抽象的组件编程时,才不会因为装饰者受到影响,如果确实是针对具体的组件编程,就需要考虑使用装饰者是否合适。

0 0
原创粉丝点击