Java设计模式--装饰器模式

1 Decorator Pattern 装饰器模式

目的:在不改变一个对象本身功能的基础上给对象增加新的行为,即增强功能;
实现:在抽象修饰类中通过聚合方式将被修饰类引入,增强功能的细节交给子类实现。

1.为了增加功能又不想增加很多子类的情况下使用;
2.动态地给一个对象增加一些额外的职责,就增加对象功能来说,装饰模式比生成子类实现更为灵活;
3.跟代理模式相比,装饰器模式强调增加新的功能。

2 实现

代码场景:在绝地救生中,大家都很喜欢98k,如果捡到6倍镜、8倍镜就更H了,找个地方愉快的等待时机,背后放枪;
98k在不装任何配件的时候仍然是可以使用的,但装了8倍镜后能进行远距离瞄准,增强它的精确度,8倍镜相对于98k来说就是装饰器;

2.1 代码实现

抽象构件角色:武器接口

public interface Weapon {
    // 入参为 倍镜的精确度
    void use(int precision);
}

具体构件角色:毛瑟98k

public class Mauser98k implements Weapon {

    public Mauser98k() {
        System.out.println("毛瑟 98k步枪射击精度高,
        经加装4倍、6倍光学瞄准镜后,可作为一种优秀的狙击步枪使用~");
    }
    @Override
    public void use(int precision) {
        if (precision >= 6) {
            System.out.println("让子弹飞一会,敌人倒下后,传来98k低沉的回声~");
        }
        if (precision < 4) {
            System.out.println("距离有点远 打偏了~");
        }
    }
}

抽象装饰类角色:高倍镜抽象类

public abstract class HighPowerLens implements Weapon {
    // 将98k聚合进来
    protected Mauser98k m98k;

    public HighPowerLens(Mauser98k m98k) {
        this.m98k = m98k;
    }
}

具体装饰类:八倍镜

public class EightTimesScope extends HighPowerLens {
    // 八倍镜的精度是8
    private final int precision = 8;

    // 调用父类构造器
    public EightTimesScope(Mauser98k m98k) {
        super(m98k);
    }

    @Override
    public void use(int precision) {
        // 调用瞄准功能
        this.aim();
        // 加装8倍镜后 增强了98k精确度
        // 使用98k进行射击
        m98k.use(this.precision);
    }

    // 瞄准方法
    private void aim() {
        System.out.println("把十字准星对准了对方的沟子~");
    }
}

2.2 涉及角色

在装饰模式结构图中包含如下几个角色:

Component(抽象构件):它是具体构件和抽象装饰类的共同父类,声明了在具体构件中实现的业务方法,它的引入可以使客户端以一致的方式处理未被装饰的对象以及装饰之后的对象,实现客户端的透明操作。

ConcreteComponent(具体构件):它是抽象构件类的子类,用于定义具体的构件对象,实现了在抽象构件中声明的方法,装饰器可以给它增加额外的职责(方法)。

Decorator(抽象装饰类):它也是抽象构件类的子类,用于给具体构件增加职责,但是具体职责在其子类中实现。它维护一个指向抽象构件对象的引用,通过该引用可以调用装饰之前构件对象的方法,并通过其子类扩展该方法,以达到装饰的目的。

ConcreteDecorator(具体装饰类):它是抽象装饰类的子类,负责向构件添加新的职责。每一个具体装饰类都定义了一些新的行为,它可以调用在抽象装饰类中定义的方法,并可以增加新的方法用以扩充对象的行为。

2.3 调用

调用者:

public class Client {
    public static void main(String[] args) {
        // 使用没有装8倍镜的98k打一枪
        Mauser98k m98k = new Mauser98k();
        System.out.println("剧情:距离太远不好瞄准--------");
        // 距离有点远可能会打偏
        // 没有安装倍镜 所以倍镜精度传入0
        m98k.use(0);

        System.out.println("剧情:舔包捡到一个8倍镜--------");
        // 使用装了8倍镜的98k打一枪
        EightTimesScope ets = new EightTimesScope(m98k);
        // 通过8倍镜的精确瞄准
        ets.use(8);
    }
}

结果:

毛瑟 98k步枪射击精度高,经加装4倍、6倍光学瞄准镜后,可作为一种优秀的狙击步枪使用~
剧情:距离太远不好瞄准--------
距离有点远 打偏了~
剧情:舔包捡到一个8倍镜--------
把十字准星对准了对方的沟子~
让子弹飞一会,敌人倒下后,传来98k低沉的回声~

代码地址:点击跳转

参考文献:
[ 1 ] 图解设计模式/(日)结城浩著;杨文轩译。–北京:人民邮电出版社,2017.1.
[ 2 ] 维基百科 设计模式
[ 3 ] 极客学院WIKI–设计模式.
[ 4 ] 菜鸟教程–设计模式.

猜你喜欢

转载自blog.csdn.net/weixx3/article/details/80153699