c++23 std::move_only_function怎么用 c++只能移动的函数包装器【详解】
发布时间 - 2025-12-29 00:00:00 点击率:次std::move_only_function 是 C++23 引入的仅支持移动语义的函数包装器,用于封装 unique_ptr、mutex 等不可拷贝的可调用对象,满足 MoveConstructible/MoveAssignable 要求,不支持拷贝和 target 相关反射接口。
std::move_only_function 是 C++23 引入的新特性,用来替代传统 std::function 中“仅支持可复制”这一限制,专为**只可移动(move-only)的可调用对象**设计。它不强制要求底层可调用对象支持拷贝,因此能包装 lambda 捕获了 unique_ptr、fstream、mutex 或其他不可拷贝资源的闭包,也能包装 std::unique_ptr<:any_callable>
等 move-only 类型。
为什么需要 move_only_function?
std::function 要求其模板参数 F 必须满足 CopyConstructible。这意味着:如果你写了一个捕获了 std::unique_ptr 的 lambda,它本身不可拷贝,就无法存入 std::function —— 编译直接失败。
而 std::move_only_function 只要求 MoveConstructible 和 MoveAssignable,彻底解除了拷贝约束,让 move-only 逻辑可以自然封装和传递。
基本用法与声明方式
它的模板形参和调用签名声明方式与 std::function 高度一致:
- 声明格式:
std::move_only_function,例如std::move_only_function - 可由任何满足调用签名且可移动的可调用对象构造:lambda(含 move-only 捕获)、函数指针、move-only functor、std::unique_ptr
等 - 不提供
.target()、.target_type()等反射接口(因 move-only 存储通常需类型擦除 + 动态分配,元信息难保全)
典型使用场景示例
以下代码展示如何包装一个带 unique_ptr 捕获的 lambda:
auto make_move_only_task() {
auto ptr = std::make_unique(42);
// 此 lambda 不可拷贝(unique_ptr 不可拷贝)
return std::move_only_function{[ptr = std::move(ptr)]() mutable {
return *ptr;
}};
}
int main() {
auto f = make_move_only_task(); // OK: 移动构造
// auto f2 = f; // ❌ 编译错误:不可拷贝
auto f3 = std::move(f); // ✅ 合法:可移动
std::cout << f3() << "\n"; // 输出 42
}
再比如包装一个临时的 std::unique_ptr<:function>> 或自定义 move-only 函数对象,也都适用。
注意事项与限制
- 不能隐式转换为函数指针(即使目标是普通函数),因为 move-only 语义与函数指针的无状态本质冲突
- 空状态检查仍用
if (f),但调用前务必判空(和 std::function 一致) - 性能上:内部通常依赖堆分配(类似 std::function),但实现可优化(如 small-buffer 优化对 move-only 类型更友好)
- 不兼容旧标准:C++20 及更早无此类型;需编译器支持(GCC 13+、Clang 16+、MSVC 19.35+)并启用
-std=c++23
它不是 std::function 的“升级版”,而是互补角色:需要拷贝时用 std::function,只需移动时用 move_only_function —— 更精准表达意图,也更安全。
# ai
# c++
# stream
# 编译错误
# 为什么
# if
# 封装
# int
# void
# Lambda
# 指针
# 接口
# fstream
# 堆
# 闭包
# 形参
# function
# 对象
# 时用
# 这一
# 如果你
# 也能
# 只需
# 也都
# 或其他
# 写了
# 自定义
# 不支持
相关栏目:
【
网站优化151355 】
【
网络推广146373 】
【
网络技术251813 】
【
AI营销90571 】
相关推荐:
如何选择PHP开源工具快速搭建网站?
高性能网站服务器部署指南:稳定运行与安全配置优化方案
Laravel事件和监听器如何实现_Laravel Events & Listeners解耦应用的实战教程
如何在 Telegram Web View(iOS)中防止键盘遮挡底部输入框
如何解决hover在ie6中的兼容性问题
EditPlus中的正则表达式 实战(2)
香港服务器建站指南:免备案优势与SEO优化技巧全解析
千库网官网入口推荐 千库网设计创意平台入口
图片制作网站免费软件,有没有免费的网站或软件可以将图片批量转为A4大小的pdf?
Midjourney怎样加参数调细节_Midjourney参数调整技巧【指南】
Win11怎么查看显卡温度 Win11任务管理器查看GPU温度【技巧】
Chrome浏览器标签页分组怎么用_谷歌浏览器整理标签页技巧【效率】
如何快速查询网站的真实建站时间?
详解免费开源的.NET多类型文件解压缩组件SharpZipLib(.NET组件介绍之七)
历史网站制作软件,华为如何找回被删除的网站?
网站制作软件免费下载安装,有哪些免费下载的软件网站?
Laravel观察者模式如何使用_Laravel Model Observer配置
Laravel如何实现数据库事务?(DB Facade示例)
Laravel如何使用Vite进行前端资源打包?(配置示例)
HTML 中动态设置元素 name 属性的正确语法详解
nginx修改上传文件大小限制的方法
专业型网站制作公司有哪些,我设计专业的,谁给推荐几个设计师兼职类的网站?
Laravel如何编写单元测试和功能测试?(PHPUnit示例)
如何利用DOS批处理实现定时关机操作详解
如何在景安服务器上快速搭建个人网站?
如何快速生成可下载的建站源码工具?
如何快速查询域名建站关键信息?
为什么php本地部署后css不生效_静态资源加载失败修复技巧【技巧】
Laravel怎么配置不同环境的数据库_Laravel本地测试与生产环境动态切换【方法】
如何快速生成ASP一键建站模板并优化安全性?
微信小程序 wx.uploadFile无法上传解决办法
Laravel如何将应用部署到生产服务器_Laravel生产环境部署流程
详解Huffman编码算法之Java实现
详解Oracle修改字段类型方法总结
JavaScript如何实现路由_前端路由原理是什么
UC浏览器如何切换小说阅读源_UC浏览器阅读源切换【方法】
Laravel如何集成第三方登录_Laravel Socialite实现微信QQ微博登录
无锡营销型网站制作公司,无锡网选车牌流程?
laravel服务容器和依赖注入怎么理解_laravel服务容器与依赖注入解析
Laravel怎么进行数据库回滚_Laravel Migration数据库版本控制与回滚操作
Laravel怎么实现验证码(Captcha)功能
微信小程序制作网站有哪些,微信小程序需要做网站吗?
laravel怎么实现图片的压缩和裁剪_laravel图片压缩与裁剪方法
中国移动官方网站首页入口 中国移动官网网页登录
使用C语言编写圣诞表白程序
如何快速搭建高效简练网站?
Laravel Sail是什么_基于Docker的Laravel本地开发环境Sail入门
Laravel如何实现全文搜索功能?(Scout和Algolia示例)
手机软键盘弹出时影响布局的解决方法
php读取心率传感器数据怎么弄_php获取max30100的心率值【指南】

