设计模式15:桥梁模式

桥梁模式(Bridge DP)的定义是:解耦抽象与实现,让两者能够分别变化。
桥梁模式的名字可能有一点费解,为什么是桥而不是别的呢?我个人理解就是像桥一样连接抽象和实现,虽然说感觉哪里怪怪的,不过也找不到更好的说法了。
至于其定义,如果了解策略模式的话应该不会陌生,因为策略模式是解耦实现,运行时切换方法族;桥梁模式就像进阶的策略模式,不仅实现策略可以切换,连实现的载体也能抽象出来然后切换。
举一个例子,《黑暗之魂》中很多武器都是Boss用玩家也能用的,那么这里就有两个抽象层面:一个是主体的抽象,可能是主角或者Boss;另一个是实现的抽象,即武器的各种攻击方式。比起每个组合创建一个对象,用乘法明显减少最终对象的数量。

代码示例:
这个例子中,抽象对应魔法武器,抽象魔法武器的实现(动作)。

抽象类魔法武器,组合一个实现的抽象,规定三个动作:

/**
 * 
 * MagicWeapon
 * 
 */
public abstract class MagicWeapon {

  protected MagicWeaponImpl imp;

  public MagicWeapon(MagicWeaponImpl imp) {
    this.imp = imp;
  }

  public abstract void wield();

  public abstract void swing();

  public abstract void unwield();

  public MagicWeaponImpl getImp() {
    return imp;
  }
}

抽象类,魔法武器实现,包含三个动作的实现方法:

/**
 * 
 * MagicWeaponImpl
 * 
 */
public abstract class MagicWeaponImpl {

  public abstract void wieldImp();

  public abstract void swingImp();

  public abstract void unwieldImp();

}

到这里其实已经比较清楚了,两个类都是抽象类,因此会派生出一些子类,魔法武器子类与魔法武器实现子类,互相之间是解耦的,可以任意搭配,也就是桥梁模式。
为了简单起见,这里只举出一个例子:
本体:

/**
 * 
 * BlindingMagicWeapon
 *
 */
public class BlindingMagicWeapon extends MagicWeapon {

  public BlindingMagicWeapon(BlindingMagicWeaponImpl imp) {
    super(imp);
  }

  @Override
  public BlindingMagicWeaponImpl getImp() {
    return (BlindingMagicWeaponImpl) imp;
  }

  @Override
  public void wield() {
    getImp().wieldImp();
  }

  @Override
  public void swing() {
    getImp().swingImp();
  }

  @Override
  public void unwield() {
    getImp().unwieldImp();
  }

  public void blind() {
    getImp().blindImp();
  }
}

实现,这里继续做了一层抽象,增加一个方法:

/**
 * 
 * BlindingMagicWeaponImpl
 *
 */
public abstract class BlindingMagicWeaponImpl extends MagicWeaponImpl {

  public abstract void blindImp();

}

然后真正的实现类:

/**
 * 
 * Excalibur
 *
 */
public class Excalibur extends BlindingMagicWeaponImpl {

  private static final Logger LOGGER = LoggerFactory.getLogger(Excalibur.class);

  @Override
  public void wieldImp() {
    LOGGER.info("wielding Excalibur");
  }

  @Override
  public void swingImp() {
    LOGGER.info("swinging Excalibur");
  }

  @Override
  public void unwieldImp() {
    LOGGER.info("unwielding Excalibur");
  }

  @Override
  public void blindImp() {
    LOGGER.info("bright light streams from Excalibur blinding the enemy");
  }
}

没错,用咖喱棒闪瞎敌人狗眼!

你可能感兴趣的:(设计模式15:桥梁模式)