桥接模式——待续

286 阅读3分钟

「这是我参与2022首次更文挑战的第14天,活动详情查看:2022首次更文挑战


哈喽,大家好,我是一条~

之前的《白话设计模式》因为工作被搁置,如今再次启航,并搭配框架源码解析一起食用,将理论与实战完美结合。

对设计模式不是很熟悉的同学可以先看一下《23种设计模式的一句话通俗解读》全面的了解一下设计模式,形成一个整体的框架,再逐个击破。

往期回顾:原型模式

今天我们一块看一下桥接模式

导图

定义

官方定义

将抽象与实现解耦,使两者都可以独立变化。

通俗解读

在某些情况下,一个类可能有多个维度的变化,如果只是用继承将会变得非常冗余甚至无法实现。

如图形既可按形状分,又可按颜色分。如果用继承方式,m 种形状和 n 种颜色的图形就有 m×n 种,不但对应的子类很多,而且扩展困难。还有不同颜色和字体的文字、不同品牌和功能的手机等等。

桥接模式就是为了解决这个问题,处理多层继承结构,处理多维度变化的场景,将各个维度设计成独立的继承结构,使各个维度可以独立的扩展在抽象层建立关联。降低类之间的耦合度,减少代码量。

结构图

桥接模式包含以下主要角色:

  • 抽象化角色:定义抽象类,并包含一个对实现化对象的引用。
  • 扩展抽象化角色:是抽象化角色的子类,实现父类中的业务方法,并通过组合关系调用实现化角色中的业务方法。
  • 实现化角色:定义实现化角色的接口,供扩展抽象化角色调用。
  • 具体实现化角色:给出实现化角色接口的具体实现。

代码演示

目录结构

建议跟着一条学设计模式的小伙伴都建一个maven 工程,并安装lombok依赖和插件。

并建立如下包目录,便于归纳整理。

pom如下

    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <version>1.16.10</version>
    </dependency>

开发场景

代码实现

新建手机抽象类:Phone

/**
 * 抽象化类
 */

@Data
public abstract class Phone {
    public String name;

   // 不同销售渠道的价格是不一样的,将这种的实现抽取出来独立变化。 
    public ASale sale;

    String getInfo() {
        return  name+" "+sale.getType()+" "+sale.getPrice();
    }
}

新建销售渠道实现化

@AllArgsConstructor
@Data
public abstract class ASale {
    private int price;
    private String type;
}

手机的实现:IPhone12IPhone12pro

public class IPhone12 extends Phone{

}
public class IPhone12pro extends Phone{

}

销售渠道的实现:

public class OfflineSale extends ASale {

    public OfflineSale(int price, String type) {
        super(price, type);
    }
}
public class OnlineSale extends ASale{

    public OnlineSale(int price, String type) {
        super(price, type);
    }
}

测试代码

public  class MainTest {
    public static void main(String[] args) {
        IPhone12 iPhone12 = new IPhone12();
        iPhone12.setName("IPhone12");
        // 价格以分为单位
        iPhone12.setSale(new OnlineSale(599900,"online"));

        String info = iPhone12.getInfo();
        System.out.println(info);

        IPhone12pro iPhone12pro = new IPhone12pro();
        iPhone12pro.setName("IPhone12pro");
        iPhone12pro.setSale(new OfflineSale(799900,"offline"));

        String proInfo = iPhone12pro.getInfo();
        System.out.println(proInfo);
    }
}

输出结果

这是如果增加IPhone12ProMax的学生优惠渠道,只需分别继承即可。

public class StuSale extends ASale{
    public StuSale(int price, String type) {
        super(price, type);
    }
}
public class IPhone12ProMax extends Phone{
}

再次测试

IPhone12ProMax iPhone12ProMax = new IPhone12ProMax();
iPhone12ProMax.setName("IPhone12ProMax");
iPhone12ProMax.setSale(new StuSale(1090000,"stu"));

String maxInfo = iPhone12ProMax.getInfo();
System.out.println(maxInfo);

输出结果

应用场景

总结