0

0

C++如何实现桥接模式?(解耦抽象与实现)

穿越時空

穿越時空

发布时间:2026-02-18 18:13:48

|

432人浏览过

|

来源于php中文网

原创

桥接模式的核心是组合加虚函数,通过abstraction持有implementor指针并多态调用,而非继承;implementor须为抽象基类,具体实现仅继承它;指针类型由生命周期归属决定,避免shared_ptr;接口需稳定,新增功能优先用默认实现。

c++如何实现桥接模式?(解耦抽象与实现)

桥接模式的核心不是继承,是组合加虚函数

桥接模式在 C++ 里最容易被写成“用继承模拟组合”——比如让 Abstraction 继承 Implementor,或者反过来。这完全违背桥接本意。它要解决的是抽象层(如 Shape)和实现层(如 Renderer)各自独立变化的问题,靠的是「持有指针 + 多态调用」,不是类层级的耦合。

关键判断:只要你在 Abstraction 里看到 public Implementor 或者 class Abstraction : public Implementor,就错了。

  • Abstraction 类里必须包含一个指向 Implementor 的指针(通常是 std::unique_ptr<implementor></implementor> 或裸指针,视生命周期而定)
  • Implementor 必须是抽象基类,定义纯虚函数(如 virtual void draw() = 0
  • 所有具体实现(OpenGLRendererSkiaRenderer)只继承 Implementor,不碰 Abstraction 体系
  • 构造 Abstraction 子类时,必须传入一个具体的 Implementor 实例,不能在内部 new

std::unique_ptr 还是 raw pointer?看谁管生命周期

桥接对象的生命周期归属决定指针类型——这不是风格选择,是责任划分问题。常见错误是 Abstraction 拿着裸指针却擅自 delete,或用 std::shared_ptr 引入不必要的循环引用。

  • 如果 Abstraction 完全拥有 Implementor(比如用户传进来一个临时对象,你希望它活到 Abstraction 销毁),用 std::unique_ptr<implementor></implementor>
  • 如果 Implementor 是全局单例或由外部长期管理(如 GUI 框架提供的 Canvas),用裸指针 + 注释说明“non-owning”,且禁止在析构中 delete
  • 避免 std::shared_ptr:桥接不涉及共享所有权,加 refcount 只会模糊职责,还可能因循环引用导致泄漏

示例:Circle 构造时接收 std::unique_ptr<renderer>&&</renderer>,移动语义保证所有权清晰;而 UIWidget 接收 Renderer* 并标注 // owned by AppContext

立即学习C++免费学习笔记(深入)”;

虚函数表开销小,但别在 hot path 上间接调用

桥接必然引入一次虚函数调用(renderer->draw()),在图形渲染等高频路径上,这比直接内联调用多 1–2 个周期。不是性能瓶颈,但容易被忽略。

  • 不要在每像素循环里调用 implementor->put_pixel();应把整块数据交给 Implementor 批处理(如 render_buffer(const uint8_t*, size_t)
  • 如果某类 Implementor 确实需要极致性能(如 SIMD 渲染),可提供非虚的模板接口(template<typename t> void fast_draw(T&&)</typename>),但桥接主干仍走虚函数,保持扩展性
  • 编译器通常能对单实现场景做 devirtualization,但别依赖——确保关键路径不卡在虚调用上

容易漏掉的:Implementor 接口变更会破坏所有子类

桥接解耦的是类结构,不是接口契约。Implementor 基类一旦增加新纯虚函数,所有派生类都得改,否则链接失败。这点比继承更隐蔽,因为改动发生在“底层”。

  • Implementor 接口设计得足够稳定:优先用组合已有接口(如 Drawable + Resizable),而不是堆大而全的基类
  • 新增能力尽量用默认实现(C++11 起支持 virtual void save_to_file() { throw std::runtime_error("not implemented"); }),而非强制重写
  • 测试时别只测 Abstraction 行为,要 mock 不同 Implementor 的行为差异,尤其验证异常路径下 Abstraction 是否正确转发错误

真正麻烦的从来不是写对桥接结构,而是当 Renderer 需要支持 Vulkan 后端时,你发现 OpenGLRendererSkiaRenderer 都得补 3 个新虚函数——这时候才意识到,接口粒度早该按能力切分,而不是按技术栈。

热门AI工具

更多
DeepSeek
DeepSeek

幻方量化公司旗下的开源大模型平台

豆包大模型
豆包大模型

字节跳动自主研发的一系列大型语言模型

通义千问
通义千问

阿里巴巴推出的全能AI助手

腾讯元宝
腾讯元宝

腾讯混元平台推出的AI助手

文心一言
文心一言

文心一言是百度开发的AI聊天机器人,通过对话可以生成各种形式的内容。

讯飞写作
讯飞写作

基于讯飞星火大模型的AI写作工具,可以快速生成新闻稿件、品宣文案、工作总结、心得体会等各种文文稿

即梦AI
即梦AI

一站式AI创作平台,免费AI图片和视频生成。

ChatGPT
ChatGPT

最最强大的AI聊天机器人程序,ChatGPT不单是聊天机器人,还能进行撰写邮件、视频脚本、文案、翻译、代码等任务。

相关专题

更多
java多态详细介绍
java多态详细介绍

本专题整合了java多态相关内容,阅读专题下面的文章了解更多详细内容。

22

2025.11.27

java多态详细介绍
java多态详细介绍

本专题整合了java多态相关内容,阅读专题下面的文章了解更多详细内容。

22

2025.11.27

c语言const用法
c语言const用法

const是关键字,可以用于声明常量、函数参数中的const修饰符、const修饰函数返回值、const修饰指针。详细介绍:1、声明常量,const关键字可用于声明常量,常量的值在程序运行期间不可修改,常量可以是基本数据类型,如整数、浮点数、字符等,也可是自定义的数据类型;2、函数参数中的const修饰符,const关键字可用于函数的参数中,表示该参数在函数内部不可修改等等。

547

2023.09.20

javascriptvoid(o)怎么解决
javascriptvoid(o)怎么解决

javascriptvoid(o)的解决办法:1、检查语法错误;2、确保正确的执行环境;3、检查其他代码的冲突;4、使用事件委托;5、使用其他绑定方式;6、检查外部资源等等。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

183

2023.11.23

java中void的含义
java中void的含义

本专题整合了Java中void的相关内容,阅读专题下面的文章了解更多详细内容。

115

2025.11.27

硬盘接口类型介绍
硬盘接口类型介绍

硬盘接口类型有IDE、SATA、SCSI、Fibre Channel、USB、eSATA、mSATA、PCIe等等。详细介绍:1、IDE接口是一种并行接口,主要用于连接硬盘和光驱等设备,它主要有两种类型:ATA和ATAPI,IDE接口已经逐渐被SATA接口;2、SATA接口是一种串行接口,相较于IDE接口,它具有更高的传输速度、更低的功耗和更小的体积;3、SCSI接口等等。

1508

2023.10.19

PHP接口编写教程
PHP接口编写教程

本专题整合了PHP接口编写教程,阅读专题下面的文章了解更多详细内容。

423

2025.10.17

php8.4实现接口限流的教程
php8.4实现接口限流的教程

PHP8.4本身不内置限流功能,需借助Redis(令牌桶)或Swoole(漏桶)实现;文件锁因I/O瓶颈、无跨机共享、秒级精度等缺陷不适用高并发场景。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

2260

2025.12.29

pixiv网页版官网登录与阅读指南_pixiv官网直达入口与在线访问方法
pixiv网页版官网登录与阅读指南_pixiv官网直达入口与在线访问方法

本专题系统整理pixiv网页版官网入口及登录访问方式,涵盖官网登录页面直达路径、在线阅读入口及快速进入方法说明,帮助用户高效找到pixiv官方网站,实现便捷、安全的网页端浏览与账号登录体验。

561

2026.02.13

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
C# 教程
C# 教程

共94课时 | 9.7万人学习

C 教程
C 教程

共75课时 | 4.8万人学习

C++教程
C++教程

共115课时 | 18.3万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号