设计模式:桥接模式(c++实现案例)

2023-11-12

桥接模式

桥接模式是一种结构型设计模式, 可将业务逻辑或一个大类拆分为不同的层次结构, 从而能独立地进行开发。桥接模式通过将继承改为组合的方式来解决这个问题。

具体来说, 就是抽取其中一个维度并使之成为独立的类层次, 这样就可以在初始类中引用这个新层次的对象, 从而使得一个类不必拥有所有的状态和行为。

层次结构中的第一层 (通常称为抽象部分) 将包含对第二层 (实现部分) 对象的引用。
抽象部分将能将一些 (有时是绝大部分) 对自己的调用委派给实现部分的对象。 所有的实现部分都有一个通用接口, 因此它们能在抽象部分内部相互替换。

桥接模式在处理跨平台应用、 支持多种类型的数据库服务器或与多个特定种类 (例如云平台和社交网络等) 的 API 供应商协作时会特别有用。

应用实例: 1、猪八戒从天蓬元帅转世投胎到猪,转世投胎的机制将尘世划分为两个等级,即:灵魂和肉体,前者相当于抽象化,后者相当于实现化。生灵通过功能的委派,调用肉体对象的功能,使得生灵可以动态地选择。 2、墙上的开关,可以看到的开关是抽象的,不用管里面具体怎么实现的。

桥接模式实现步骤

1.提供一个抽象类(桥接类):提供高层控制逻辑,依赖实际底层对象

2.提供一个具体抽象类:拓展抽象类,更精确的抽象

3.提供具体实现抽象类:具体实现类的抽象通用接口

4.提供具体实现类:针对不同底层的通用接口实现


代码实现:

#include <iostream>
#include <string>
#include <vld.h>
using namespace std;

//1. 作为桥接实现的color类
class color
{
public:
	virtual ~color() {}
	virtual void FillColor() = 0;
};
//2.1 实现了color的具体类
class Red :public color
{
public:
	Red() :colorType("RED") {}
	~Red() {}
	void FillColor()override
	{
		cout << "填充颜色:" << colorType << endl;
	}
private:
	string colorType;
};
//2.2 实现了color的具体类
class Blue :public color
{
public:
	Blue() :colorType("BLUE") {}
	~Blue() {}
	void FillColor()override
	{
		cout << "填充颜色:" << colorType << endl;
	}
private:
	string colorType;
};

//3. 具体实现抽象类,提供实现接口定义
class Shape
{
public:
	virtual ~Shape() { if (m_color) { delete m_color; m_color = nullptr; } }
	virtual void showShape() = 0;
	virtual void setColor(color* color) = 0;
protected:
	virtual void drawColor() = 0;
	virtual void drawShape() = 0;
	color* m_color;
};

//4.1 具体实现类:实现接口
class Circle :public Shape
{
public:
	Circle() :shapeType("Circle") {}
	~Circle() { }
	void showShape()override
	{
		drawColor();
		drawShape();
	}
	void setColor(color* color)override
	{
		if (m_color) { delete m_color; m_color = nullptr; }
		this->m_color = color;
	}
private:
	void drawColor()override
	{
		this->m_color->FillColor();
	}
	void drawShape()override
	{
		cout << "绘制:" << shapeType << endl;
	}
	string shapeType;
};
//4.2 具体实现类:实现接口
class Rect :public Shape
{
public:
	Rect() :shapeType("Rect") {}
	~Rect() {}
	void showShape()override
	{
		drawColor();
		drawShape();
	}
	void setColor(color* color)override
	{
		if (m_color) { delete m_color; m_color = nullptr; }
		this->m_color = color;
	}
private:
	void drawColor()override
	{
		this->m_color->FillColor();
	}
	void drawShape()override
	{
		cout << "绘制:" << shapeType << endl;
	}
	string shapeType;
};

int main()
{
	Shape* circle = new Circle;
	circle->setColor(new Red);
	circle->showShape();
	circle->setColor(new Blue);
	circle->showShape();
	delete circle;
	circle = nullptr;

	Shape* rect = new Rect;
	rect->setColor(new Red);
	rect->showShape();
	rect->setColor(new Blue);
	rect->showShape();
	delete rect;


	return 0;
}

优点

  • 你可以创建与平台无关的类和程序

  • 客户端代码仅与高层抽象部分互动, 不接触到平台详细信息

  • 开闭原则,可以新增抽象和实现, 且它们之间互不影响

  • 单一职责原则,抽象专注高层逻辑, 实现部分处理平台细节

缺点

  • 对高内聚的类使用该模式可能会让代码更加复杂
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

设计模式:桥接模式(c++实现案例) 的相关文章

  • 使用链表进行堆排序

    我想知道是否有人曾经使用链表进行堆排序 如果他们可以提供代码 我已经能够使用数组进行堆排序 但尝试在链表中进行排序似乎不切实际 而且在你知道的地方很痛苦 我必须为我正在做的项目实现链接列表 任何帮助将不胜感激 我也用C 答案是 你不想在链表
  • C# 静态类型不能用作参数

    public static void SendEmail String from String To String Subject String HTML String AttachmentPath null String Attachme
  • 如何从字符串中提取子字符串直到遇到第二个空格?

    我有一个像这样的字符串 o1 1232 5467 1232 5467 1232 5467 1232 5467 1232 5467 1232 5467 如何仅提取 o1 1232 5467 要提取的字符数并不总是相同 因此 我只想提取直到遇到
  • 格式说明符%02x

    我有一个简单的程序 include
  • 捕获 .aspx 和 .ascx 页面中的异常

    问题说明了一切 请看以下示例代码 ul li li ul
  • C# 中的 Stack<> 实现

    我最近一直在实现递归目录搜索实现 并且使用堆栈来跟踪路径元素 当我使用 string Join 连接路径元素时 我发现它们被颠倒了 当我调试该方法时 我查看了堆栈 发现堆栈内部数组中的元素本身是相反的 即最近 Push 的元素位于内部数组的
  • Boost ASIO 串行写入十六进制值

    我正在使用 ubuntu 通过串行端口与设备进行通信 所有消息都必须是十六进制值 我已经在 Windows 环境中使用白蚁测试了通信设置 并得到了我期望的响应 但在使用 Boost asio 时我无法得到任何响应 以下是我设置串口的方法 b
  • 如何在 C# 中将 Json 转换为对象

    我想将 Json 转换为 C 中的对象 这里的 Json 是 值 e920ce0f e3f5 4c6f 8e3d d2fbc51990e4 如何使用 Object 问题看似愚蠢 但其实并不那么愚蠢 我没有简单的 Json 我有 IEnume
  • 防止控制台应用程序中的内存工作集最小化?

    我想防止控制台应用程序中的内存工作集最小化 在Windows应用程序中 我可以这样做覆盖 SC MINIMIZE 消息 http support microsoft com kb 293215 en us fr 1 但是 如何在控制台应用程
  • MVC 5 中具有 ASP.NET Identity 的 Autofac 不会验证 OWIN 管道中的安全标记

    我在 MVC 5 中设置了 AutoFac 来与 ASP NET Identity 一起使用 表面上一切似乎都工作正常 即用户可以创建帐户并登录 但后来我发现 当安全标记更改时 用户不会注销 通过在 AspNetUsers 表中进行暴力破解
  • Makefile 和 .Mak 文件 + CodeBlocks 和 VStudio

    我对整个 makefile 概念有点陌生 所以我对此有一些疑问 我正在 Linux 中使用 CodeBlocks 创建一个项目 我使用一个名为 cbp2mak 的工具从 CodeBlocks 项目创建一个 make 文件 如果有人知道更好的
  • LinkLabel 无下划线 - Compact Framework

    我正在使用 Microsoft Compact Framework 开发 Windows CE 应用程序 我必须使用 LinkLabel 它必须是白色且没有下划线 因此 在设计器中 我将字体颜色修改为白色 并在字体对话框中取消选中 下划线
  • 使用 gcc 时在头文件中查找定义的好方法是什么?

    在使用 gcc 时 有人有推荐的方法在头文件中查找定义吗 使用 MSVC 时 我只需右键单击并选择 转到定义 这非常好 我使用过 netbeans gcc 它确实有代码帮助 包括到定义的超链接 所以这是一种选择 但是 我想知道是否有任何其他
  • Unity3D - 将 UI 对象移动到屏幕中心,同时保持其父子关系

    我有一个 UI 图像 它的父级是 RectTransform 容器 该容器的父级是 UI 面板 而 UI 面板的父级是 Canvas 我希望能够将此 UI 图像移动到屏幕中心 即画布 同时保留父级层次结构 我的目标是将 UI 图像从中心动画
  • 调用 .ToArray() 时出现 ArgumentException

    我有一个经常被清除的列表 代码完全是这样的 VisitorAgent toPersist List
  • C:设置变量范围内所有位的最有效方法

    让我们来int举个例子 int SetBitWithinRange const unsigned from const unsigned to To be implemented SetBitWithinRange应该返回一个int其中所有
  • 在 C# 的 WebAPI 中的 ApiController 上使用“传输编码:分块”提供数据

    我需要服务分块传输使用编码数据API控制器 因为我无权访问HttpContext or the Http请求 我有点不知道在哪里写入响应以及在哪里刷新它 设置如下 public class MyController ApiControlle
  • 如何获取带有某个属性注释的所有属性?

    我刚刚从 Roslyn 开始 我想找到所有用属性名称 OneToOne 注释的属性 我启动了 SyntaxVisualizer 并能够获取对该节点的引用 但我想知道是否有更简单的方法来实现此目的 这就是我所拥有的 var prop docu
  • Streamwriter 覆盖 txt 文件中的文本

    有没有什么方法可以重新打开流写入器而不创建新的写入对象 因为此时 当调用 WriteOdd 时 streamwriter 正在覆盖在它之前调用的 WriteEven public void WriteEven StreamWriter wr
  • 声明一个负长度的数组

    当创建负长度数组时 C 中会发生什么 例如 int n 35 int testArray n for int i 0 i lt 10 i testArray i i 1 这段代码将编译 并且启用 Wall 时不会出现警告 并且似乎您可以分配

随机推荐

  • 【python】实现list除以一个数

    文章目录 新建一个list 存放数据 使用numpy np divide list如何除以一个数 有如下两种方法 import random my list random randint 0 100 for x in range 10 pr
  • mysql 页和叶子页_一看就懂的:MySQL数据页以及页分裂机制,别在说不会了

    下面我们就一起看下 究竟什么是MySQL的数据页 数据区等概念 二 数据页长啥样 数据页长下面这样 image png 三 什么是数据区 在MySQL的设定中 同一个表空间内的一组连续的数据页为一个extent 区 默认区的大小为1MB 页
  • MySQL Flashback拯救手抖党

    MySQL Flashback拯救手抖党 2019 06 12 黄子程 黄子程 黄子程 网易游戏资深运维工程师 曾参与多款网易代理游戏产品的运营维护工作 后逐渐转向数据库管理维护领域 目前主要工作方向为网易游戏 Relational DBa
  • unity3d 对大图额外加载

    加载 UI 背景大图 lua 使用 if self findBack image nil then resMgr UnLoadBigImage self findBack image self findBack image nil self
  • 【华为云】E: You don‘t have enough free space in /var/cache/apt/archives/.

    目录 一 购买华为云系统盘空间 二 扩容前的准备 三 扩容 扩大已有MBR分区 起因 使用华为云服务器 在安装Xfce桌面环境时报错 E You don t have enough free space in var cache apt a
  • sql 数据库删除,修改,增加列语句

    ALTER TABLE 添加 修改 删除表的列 约束等表的定义 查看列 desc 表名 修改表名 alter table t book rename to bbb 添加列 alter table 表名 add column 列名 varch
  • [翻译&摘抄]ES6 中的元编程:Symbol

    原文地址 Metaprogramming in ES6 Symbols and why they re awesome 原文作者 Keith Cirkel 译文出自 掘金翻译计划 转自 https juejin im post 5a0e65
  • LM5118 DC-DC电源降压芯片带载能力不够问题

    1 现象 主机系统带载到2A时 系统反复重启 2 分析 示波器测量VCC 5V 稳压源一显示到2A VCC 5V就会掉到0V 把如下二极管断开 万用表测量电流到3 7A就是掉下 3 解决 查规格书可知电流检测电阻的计算 原来为0 03R 按
  • javascript解析XML生成树形结构

    前两天一个朋友去一家公司面试 面试题是用javascript解析一个XML 生成树形结构 今天闲着没事就试了试 源代码
  • Unity自带的相应事件

    Unity自带的相应事件 代码 条件 各个响应事件 鼠标移入移出 鼠标按下 抬起 点击 鼠标拖拽 选择事件接口 系统按键事件的接口 代码 using UnityEngine using UnityEngine EventSystems pu
  • 数据结构题目-哈希

    目录 A Hash表 线性探测法解决冲突 B 求3阶B 树的深度 C 输出3阶B 树的构造过程 D Hash表 链表法解决冲突 仅作储存代码使用 A Hash表 线性探测法解决冲突 include
  • Python当中reverse()函数

    Hello大家好 今天我想和大家分享一下Python当中的reverse 函数 reverse 函数顾名思义就是反转的意思 但是我们要注意反转的内容只能是python当中的列表 千万不要忘记了 例子如下 arr 1 2 3 4 5 6 ar
  • js数据类型之对象object类型(数组与自定义对象)

    对象object 数组与自定义对象 JavaScript 中的所有事物都是对象 字符串 数值 数组 函数 此外 JavaScript 允许自定义对象 JavaScript 提供多个内建对象 比如 String Date Array 等等 对
  • CoordinatorLayout+AppBarLayout+CollapsingToolbarLayout+Toolbar实现渐变透明的状态栏

    在之前的一篇博文里面我已经说明了CoordinatorLayout使用过程中遇到的问题 之后又发现结合CollapsingToolbarLayout使用时的另一个问题 CollapsingToolbarLayout里面的ImageView为
  • [架构之路-208]- 人人都是产品经理 - 什么是产品经理?产品经理具体是做什么的?

    目录 一 什么是产品经理 产品经理具体做什么 二 产品经理的岗位职责 三 产品经理的职业规划 一 什么是产品经理 产品经理具体做什么 在外行人看来 产品经理常常被误认为是 经理 其实产品经理只是一个岗位名称 并不是真正意义上的 经理 或者说
  • 深入浅出UML类图(五)

    实例分析3 售票机控制程序 某运输公司决定为新的售票机开发车票销售的控制软件 图I给出了售票机的面板示意图以及相关的控制部件 图I 售票机面板示意图 售票机相关部件的作用如下所述 1 目的地键盘用来输入行程目的地的代码 例如 200表示总站
  • python的几个重要基本概念

    1 整数 小数 布尔值和空值 整数 int类型 计算机中整数是有最大值的 与计算机的存储能力有关 即使是这样计算机中的整数值也是很大很大的 这一点基本上不需要担心的 小数 也称 浮点数 float类型 小数就是带小数点的数包括 1 0 等等
  • sqlite数据库-------清除数据,数据库文件大小不变解决方法

    现象 删除表格的全部数据 DELETE FROM Name 原因 当在sqlite中删除了大量数据后 数据库文件的大小还是那样 没有变 原因是 从Sqlite删除数据后 未使用的磁盘空间被添加到一个内在的 空闲列表 中用于存储你下次插入的数
  • IP协议号与传输层端口

    网络层 数据包的包格式里面有个很重要的字段叫做协议号 比如在传输层如果是tcp连接 那么在网络层ip包里面的协议号就将会有个值是6 如果是udp的话那个值就是17 传输层 传输层 通过接口关联 端口的字段叫做端口 应用层 协议号是存在于IP
  • 设计模式:桥接模式(c++实现案例)

    桥接模式 桥接模式是一种结构型设计模式 可将业务逻辑或一个大类拆分为不同的层次结构 从而能独立地进行开发 桥接模式通过将继承改为组合的方式来解决这个问题 具体来说 就是抽取其中一个维度并使之成为独立的类层次 这样就可以在初始类中引用这个新层