新闻中心

C++的std::unique_ptr如何自定义删除器_为C++智能指针指定特殊的资源释放逻辑

2025-12-15
浏览次数:
返回列表
自定义删除器用于适配非标准资源释放方式,如malloc内存或C API句柄。1. 可用函数指针定义简单删除器,如free_deleter释放malloc内存;2. 用lambda结合decltype指定类型,实现灵活清理,如关闭文件;3. 使用仿函数定义复杂逻辑删除器,如SDL_Surface_deleter调用SDL_FreeSurface;4. 注意删除器影响类型大小,无状态更高效,且需处理空指针与异常安全。

c++的std::unique_ptr如何自定义删除器_为c++智能指针指定特殊的资源释放逻辑

在C++中,std::unique_ptr 默认使用 delete 来释放所管理的对象。但在某些场景下,资源的释放方式并非简单的 delete,比如用 malloc 分配的内存、C 风格 API 创建的文件句柄、或通过特定函数(如 SDL_FreeSurface)释放资源等。这时就需要为 std::unique_ptr 指定自定义删除器来正确回收资源。

自定义删除器的作用

自定义删除器是一个可调用对象(函数指针、函数对象、lambda 等),它定义了 unique_ptr 在析构时如何释放资源。通过指定删除器,可以让智能指针适配各种非标准的资源管理方式。

如何为 unique_ptr 添加自定义删除器

有两种常见方式:函数指针和函数对象(仿函数)。以下分别说明:

● 使用函数指针作为删除器

适用于简单的 C 风格清理函数。例如,释放由 malloc 分配的内存:

#include <memory>
#include <cstdlib>
<p>// 删除器函数
void free_deleter(int* ptr) {
std::free(ptr);
}</p><p>// 声明 unique_ptr 并指定删除器类型
std::unique_ptr<int, void(<em>)(int</em>)> ptr(
static_cast<int*>(std::malloc(sizeof(int))),
free_deleter
);</p><p>// 当 ptr 离开作用域时,会自动调用 free_deleter

● 使用 lambda 表达式(需配合 std::function 或直接推导)

更灵活的方式是使用 lambda,但注意不能直接用于模板参数(除非用 auto 推导)。通常结合 decltype 显式声明类型:

AI Code Reviewer AI Code Reviewer

AI自动审核代码

AI Code Reviewer 112 查看详情 AI Code Reviewer
auto deleter = [](FILE* f) {
    if (f) std::fclose(f);
};
<p>std::unique_ptr<FILE, decltype(deleter)> file_ptr(std::fopen("test.txt", "r"), deleter);</p><p>// 文件会在离开作用域时自动关闭

● 使用函数对象(仿函数)

定义一个类并重载 operator(),适合需要状态或复杂逻辑的删除器:

struct SDL_Surface_deleter {
    void operator()(SDL_Surface* ptr) const {
        if (ptr) SDL_FreeSurface(ptr);
    }
};
<p>std::unique_ptr<SDL_Surface, SDL_Surface_deleter> surface_ptr(
IMG_Load("image.png")
);

注意事项与最佳实践

自定义删除器会影响 unique_ptr 的类型大小。如果删除器是函数指针或空 lambda,通常不会增加开销;但如果删除器包含状态(如捕获变量的 lambda),可能导致智能指针变大。

  • 尽量使用无状态 lambda 或函数指针以保持轻量
  • 避免在删除器中抛出异常
  • 确保删除器能正确处理空指针(如 fclose 可以,但有些 API 不行)
  • 构造 unique_ptr 时必须同时传入指针和删除器

基本上就这些。只要理解删除器的本质是一个“怎么释放”的策略,就能灵活应用于各种资源管理场景。

以上就是C++的std::unique_ptr如何自定义删除器_为C++智能指针指定特殊的资源释放逻辑的详细内容,更多请关注其它相关文章!


# 但在  # 自学网络推广的网站  # 网站引流推广诈骗犯法吗  # 江苏昆山建设网站  # 抖音seo 黑产  # 松岗免费网站优化公司  # 批量seo关键词Shopify  # 有网站怎样做推广  # 安顺仪器仪表网站推广  # 株洲网站建设中标公示  # 外贸网站建设交流  # 适用于  # c++智能指针  # 就能  # 有哪些  # 面试题  # 非标准  # 资源管理  # 句柄  # 是一个  # 自定义  # 作用域  # c++  # 自定义删除器 


相关栏目: 【 科技资讯46185 】 【 网络学院92790


相关推荐: Python Socket多播通信中指定源IP地址的实践指南  J*aScript map 方法中处理循环元素为空数组的策略  163邮箱官方主页登录 直达网易邮箱登录核心页面  PowerPoint如何制作滚动字幕结尾彩蛋_PowerPoint路径动画实现平滑滚动字幕效果  使用 Pandas 高效处理 .dat 文件:字符清理与数据计算  深入理解rpy2中的类型转换:优化Python对象到R矩阵的映射  漫画星球免费下拉式入口 漫画星球免费漫画在线阅读网站  Fabric Mod开发:在1.19.3+版本中正确添加自定义物品并管理物品组  谷歌学术网站直达地址 谷歌学术搜索网页版一键进入  微博网页版直接访问 微博网页版账号管理快速入口  Surface怎么安装系统 微软Surface Pro U盘重装win11教程  CSS图片焦点样式实现教程:理解与应用tabindex属性  在哪找SublimeJ远程工具_SFTP插件配置教程  Win10双系统截图高效法 截屏快捷键速记【技巧】  汽水音乐在线解析 汽水音乐在线解析入口  凉拌黄瓜怎么拌更入味 凉拌黄瓜简单家常做法  J*aScript中如何高效提取对象指定属性  高德地图总提示网络异常怎么办 高德地图离线导航设置与网络排查方法  如何创建没有密码的Windows本地账户_跳过微软账户登录的技巧【教程】  小红书网页版入口链接分享 小红书官网直接进  照顾宝贝2小游戏免费秒玩入口  PPT平滑切换怎么做 PPT炫酷“平滑”切换动画制作教程【必学】  漫蛙manwa2最新登录网址_漫蛙manwa2手机网页版入口  Mac终端命令大全_Mac常用Terminal指令速查  composer 和 npm/yarn 在管理依赖方面有什么核心思想差异?  Yandex免登录官网入口_俄罗斯Yandex搜索引擎直达链接  文心一言怎样用插件调度API数据_文心一言用插件调度API数据【API调用】  如何有效阻止外部脚本意外修改内联样式的高度属性  汽水音乐车机版8.9下载 汽水音乐车机版8.9版本安装入口  DLsite中文平台入口 DLsite官网内容在线查看  深入理解与实现最大堆的Heapify过程:常见错误与修正  J*aScript设计模式实践_j*ascript代码优化  C++ string find函数返回值npos详解_C++字符串查找失败的判断条件  解决Flask中Quill编辑器内容提交失败及TypeError的指南  J*aScript井字棋(Tic-Tac-Toe)核心交互逻辑实现教程  Spring Boot内嵌服务器与J*a EE全栈特性:选择与部署策略  QQ邮箱官方登录入口_QQ邮箱网页版快捷使用平台  C++如何操作大型数据集_使用C++流式处理(Streaming)技术避免一次性加载大文件  Sublime Text怎么显示空格和制表符_Sublime显示不可见字符设置  怎么在mac上运行html代码_mac运行html代码方法【指南】  Mac怎么锁定备忘录_Mac备忘录加密设置教程  Golang如何优雅处理error_Golang error处理最佳实践总结  如何提高微信支付的安全性_微信支付安全防护与设置建议  夸克浏览器图书入口 夸克手机浏览器阅读入口  为什么简单的XML文件也会解析失败? 检查隐藏的非打印字符(如BOM)的方法  蛙漫限时开放最深处链接_蛙漫全站漫画会员同款秒开地址  PrimeNG Sidebar背景色自定义指南:CSS覆盖与主题化实践  小米汽车11月交付量突破40000台!雷军:将继续努力  如何在更新Composer依赖后自动运行测试_使用post-update-cmd钩子触发PHPUnit  Win11如何开启讲述人功能 Win11屏幕阅读器(讲述人)开启与关闭【教程】 

搜索