装饰模式

这里没有对装饰模式的讲解,只有自己的理解和一些代码示例。下图是我对各个组件的命名。

1、动态的为一个对象增加新的功能

2、装饰模式是一种用于代替继承的技术,无需通过继承增加子类就能扩展对象的新功能(这样就比卖你了因为继承导致的同类型体系的快速膨胀 )。使用对象的关联关系代替继承关系,更加灵活。

3、设计原则:类应该对扩展开放,对修改关闭。在不修改先有代码的情况下,而已搭配新的行为,这样使设计具有了弹性,可以应对改变,可以接收新的功能来应对改变的需求。

4、利用继承设计子类的行为,是在编译时静态决定的,而装饰模式可以在任何时候被装饰,所以可以在运行时动态地,不限量的用自己喜欢的装饰者来装饰对象

5、装饰者通常是用其他类似于工厂或生成器这样的模式创建的。

6、装饰模式的缺点会产生非常多的小对象,就比如IO中的众多对象,所有就需要了解装饰者的工作原理,次啊能容易的分辨出他们的装饰者类是如何组织的。

先写一个简单的装饰模式:(车有基本在路上跑的功能,还增加了可以水里游,天上飞,自动驾驶的功能)

注:本例子的抽象组件使用的接口,在抽象装饰类中进行了对具体组件的引用。

类图:

//抽象组件
public interface ICar {

    void move();
}
//具体组件(真实对象)
class Car implements ICar{

    @Override
    public void move() {
        System.out.println("陆上跑");
    }
}
//抽象装饰类
class SupperCar implements ICar{

    ICar iCar;   //对真实对象的应用放置在了抽象装饰类中

    public SupperCar(ICar iCar) {
        this.iCar = iCar;
    }

    @Override
    public void move() {
        iCar.move();
    }
}
//具体装饰者 1
class FlyCar extends SupperCar{

    public FlyCar(ICar icar) {
        super(icar);
    }

    public void fly(){
        System.out.println("可以飞");
    }

    @Override
    public void move() {
        super.move();
        fly();
    }
}
//具体装饰者 2
class WaterCar extends SupperCar{

    public WaterCar(ICar icar) {
        super(icar);
    }

    public void water(){
        System.out.println("水里游");
    }

    @Override
    public void move() {
        super.move();
        water();
    }
}
//具体装饰者 3
class AutoCar extends SupperCar{

    public AutoCar(ICar icar) {
        super(icar);
    }

    public void auto(){
        System.out.println("自动驾驶");
    }

    @Override
    public void move() {
        super.move();
        auto();
    }
}
public class Test {

    public static void main(String[] args) {
        //先定义一个真实的角色
        Car car = new Car();
        car.move();

        System.out.println("新增飞行的功能-------");
        FlyCar flyCar = new FlyCar(car); //直接引用对象
        flyCar.move();

        System.out.println("新增飞行的功能-------");
        WaterCar waterCar = new WaterCar(new FlyCar(new Car())); //通过new的方式封装对象
        waterCar.move();  //这里最里面的new Car()是真实的对象,装饰了一层FlyCar的功能,然后又装饰了一层WaterCar的功能

    }
}

结果:

陆上跑
新增飞行的功能-------
陆上跑
天上飞
新增飞行的功能-------
陆上跑
天上飞
水里游

写一个复杂的装饰者模式:(为多种咖啡增加多种调料,计算总价格)

注:本例子中的抽象组件使用的抽象类,对具体组件的引用放置在了具体装饰类中。

类图:

//抽象组件
public abstract class Beverage {

    String description = "Unknown Beverage";

    public String getDescription() {

        return description;
    }

    public abstract double cost();  //计算价格,增加了调料后会增加咖啡价格
}
//具体组件 1
public class Espresso extends Beverage {

    public Espresso() {
        
        description = "Espresso coffee";
    }

    @Override
    public double cost() {
        return 1.99;
    }
}

//具体组件 2
public class DarkRoast extends Beverage {

    public DarkRoast() {
        description = "DarkRoast coffee";
    }

    @Override
    public double cost() {
        return .99;
    }
}

//具体组件 3
public class HouseBlend extends Beverage {

    public HouseBlend() {
        description = "House Blend Coffee";
    }

    @Override
    public double cost() {
        return .89;
    }
}

//具体组件 4
public class Decat extends Beverage{

    public Decat() {
        description = "Decat coffee";
    }

    @Override
    public double cost() {
        return 1.05;
    }
}
//抽象装饰类
public class CondimentDecorator extends Beverage {

    @Override
    public String getDescription() {
        return super.getDescription();
    }

    @Override
    public double cost() {
        return 0;
    }
}
//具体装饰类 1
public class Mocha extends CondimentDecorator {

    Beverage beverage;

    public Mocha(Beverage beverage) {
        this.beverage = beverage;
    }

    public String getDescription() {
        return beverage.getDescription()+", Mocha";
    }

    @Override
    public double cost() {
        return .20 + beverage.cost();
    }
}

//具体装饰类 2
public class Soy extends CondimentDecorator {

    Beverage beverage;

    public Soy(Beverage beverage) {
        this.beverage = beverage;
    }

    @Override
    public String getDescription() {
        return beverage.getDescription()+", Soy";
    }

    @Override
    public double cost() {
        return .15+ beverage.cost();
    }
}

//具体装饰类 3
public class Whip extends CondimentDecorator {

    Beverage beverage;

    public Whip(Beverage beverage) {
        this.beverage = beverage;
    }

    @Override
    public String getDescription() {
        return beverage.getDescription() + ", Whip";
    }

    @Override
    public double cost() {
        return .10 + beverage.cost();
    }
}
//开始订咖啡
public class StarbuzsCoffee {

    public static void main(String[] args) {
        Beverage beverage = new Espresso();
        System.out.println(beverage.getDescription() + " $" + beverage.cost());

        Beverage beverage1 = new DarkRoast();
        beverage1 = new Mocha(beverage1);
        beverage1 = new Mocha(beverage1);
        beverage1 = new Whip(beverage1);
        System.out.println(beverage1.getDescription() + " $" + beverage1.cost());

        Beverage beverage2 = new HouseBlend();
        beverage2 = new Mocha(beverage2);
        beverage2 = new Whip(beverage2);
        System.out.println(beverage2.getDescription() + " $" + beverage2.cost());
    }
}

结果:

Espresso coffee $1.99
DarkRoast coffee, Mocha, Mocha, Whip $1.49
House Blend Coffee, Mocha, Whip $1.1900000000000002

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值