首页 > 其他分享 >桥接模式

桥接模式

时间:2023-01-08 21:12:21浏览次数:53  
标签:BigDecimal 桥接 ProfitCal 模式 实现 ProjectProfitCal public

概述

《设计模式》中对于 “桥接模式” 的动机描述如下:

将抽象部分与它的实现部分分离,使他们可以独立地变化

桥接模式的类结构图一般如下所示:

Bridge.png

一般在以下几个场景使用桥接模式:

  • 不希望抽象和它的实现之间有一个固定的绑定关系
  • 类的抽象以及它的实现可以通过生成子类的方式加以扩充
  • 对一个抽象的实现部分的修改应对客户端不会产生影响
  • 希望在多个对象之间共享实现,但同时需要对客户端隐藏这一点

具体实例

现在需要对一期的利润数据进行处理,对于不同的公司来讲,计算的规则可能有所不同。假设我们现在需要计算和项目相关的利润数据,定义对应的计算抽象接口如下:

import java.math.BigDecimal;

public abstract ProjectProfitCal {
    public void operation() {
        // 具体业务逻辑
    }
    
	abstract BigDecimal sumForData(List<? extends ProjData> data);
}

interface ProjData {
    BigDecimal val();
}

假设现在有两家公司有不同的计算方法,现在定义两个实现类以实现利润的相关计算, Tina 公司的计算方式如下:

public class TinaProjectProfit extends ProjectProfitCal {
    @Override
    public BigDecimal sumForData(List<? extends ProjData> data) {
        return BigDecimal.valueOf(0);
    }
}

另外一家公司 Mike 的计算实现如下:

public class MikeProjectProfit implements ProjectProfitCal {
    @Override
    public BigDecimal sumForData(List<? extends ProjData> data) {
       return BigDecimal.valueOf(1);
    }
}

如果没有特殊的需求变动,那么这些代码就能够正常使用,不会有问题。但随着需求的变更,在这个项目利润计算的基础上,需要增加对项目下相关产品利润的计算,如果没有特殊的需求,直接修改 ProjectProfitCal 貌似也是可行的,但是当实现类变多的时,特别是接口与实现在不同的包中时,这种解决方式是不太适合使用的。可能想到的另一种方式是定义一个 ProjectProfitCal 的子类用于专门计算产品相关的利润,但是这同样要求定义相关的子类去实现这个接口,因此这种方式也是不太可行的

使用桥接模式,可以将具体的需求和相关的实现分离,定义相关利润计算的抽象 ProfitCal

public interface ProfitCal {
    BigDecimal calProfit(List<? extends ProjData> data); // 计算相关数据的可获取利润
}

此时可以将 ProjectProfitCal 改为组合 ProfitCal 的模式:

public abstract ProjectProfitCal {
    private final ProfitCal cal;
    
    protected ProjectProfitCal(ProfitCal cal) {
        this.cal = cal;
    }
    
    public void operation() {
        // 具体业务逻辑
    }
}

此时对于 TinaProjectProfitMikeProjectProfit 来讲,只需要实现 ProfitCal 接口来实现与 ProjectProfitCal 的硬关联:

class TinaProjectProfit implements ProfitCal {
    @Override
    public BigDecimal calProfit(List<? extends ProjData> data) {
        return BigDecimal.valueOf(0);
    }
}

class MikeProjectProfit implements ProfitCal {
    @Override
    public BigDecimal calProfit(List<? extends ProjData> data) {
        return BigDecimal.valueOf(1);
    }
}

之后,如果有其它公司的的计算方式,同样也只需要实现 ProfitCal,并且即使需求需要另外计算相关产品期的利润信息,只需要继承 ProjectProfitCal 扩展相关的业务功能,同时复用 ProfitCal 接口即可(实现 ProfitCal 接口以实现计算算法)

总结

桥接模式和 抽象工厂模式很像,都是通过组合的方式替换继承的方式来提高类的灵活性,尽管一般推荐使用 “组合” 来替换 “继承”,但是还是需要结合现有的上下文采取合适的处理模式


参考:

[1] 《设计模式—可复用面向对象基础》

标签:BigDecimal,桥接,ProfitCal,模式,实现,ProjectProfitCal,public
From: https://www.cnblogs.com/FatalFlower/p/17035352.html

相关文章

  • 09.(结构型模式)java设计模式之装饰器模式
    一、什么是装饰器模式简介:也叫包装设计模式,属于结构型模式,它是作为现有的类的一个包装,允许向一个现有的对象添加新的功能,同时又不改变其结构。给对象增加功能,一般两种......
  • 08.(结构型模式)java设计模式之组合模式
    一、什么是组合模式简介:组合模式(CompositePattern),又叫部分整体模式,它创建了对象组的树形结构。将对象组合成树状结构以表示“整体-部分”的层次关系。组合模式依据树......
  • 07.(结构型模式)java设计模式之桥接模式
    一、什么是桥接模式模式桥梁模式的用意是“将抽象化(Abstraction)与实现化(Implementation)脱耦,使得二者可以独立地变化”应用场景系统需要在构件的抽象化角色和具体化......
  • 06.(结构型模式)java设计模式之适配器模式
    一、什么是适配器模式(AdapterPattern)作为两个不兼容的接口之间的桥梁,适配器模式使得原本由于接口不兼容而不能一起工作的两个类可以一起工作。适配器模式包括3种形式:......
  • 3108 9361 9460等卡在浪潮两路机器UEFI模式下配置步骤
    1.RAID卡信息查看以及相关设置1.1开机进入到BIOS的RAID界面开机在浪潮LOGO处按”Delete”键进入到BIOS操作界面,选择”Advanced”选项,如下图:  择”AVAGOMegaRAID......
  • 浅谈PHP设计模式的状态模式
    简介:状态模式,属于行为型的设计模式。当一个对象的内在状态发生改变时,允许改变其行为,这个对象看起来像是改变了其类。适用场景:控制一个对象的状态改变过于复杂时,把状态......
  • 设计模式之美
    设计模式1.为什么要学习设计模式:应对面试中的设计模式相关问题;告别写呗别人吐槽的烂代码;提高复杂代码的设计和开发能力;让读源码、学框架事半功倍;为你的职场发展做......
  • 设计模式-状态变化-State、Memento
    状态模式上述代码缺点:如果增加一个Stat,要加很多ifelse改进方法Memento备忘录模式如果快照多了比如50次redo/需要用到一些复杂的技术,比如序列化......
  • 设计模式学习笔记
    静态工厂工厂方法可以隐藏创建产品的细节,且不一定每次都会真正创建产品,完全可以返回缓存的产品,从而提升速度并减少内存消耗。里氏替换原则返回实现接口的任意子类都可以......
  • 【Redis技术探索】「数据迁移实战」手把手教你如何实现在线+离线模式进行迁移Redis数
    从实战出发使用RedisShake进行Redis数据在线+离线模式迁移指南RedisShake基本介绍​​RedisShake​​是基于​​redis-port​​基础上进行改进的是一款开源的Redis迁移工具,......