C++中如何调用被std::shared_ptr包裹的std::function对象?
问题排查与解决
核心错误点
std::function签名定义非法std::function的模板参数必须传入完整的函数签名,你需要的是无参返回std::shared_ptr<MyClass>的函数,所以正确的签名应为std::function<std::shared_ptr<MyClass>()>,你漏写了表示无参的空括号,导致该类型本身不具备合法的调用运算符,这是解引用后调用仍报错的根本原因。
- 智能指针初始化逻辑错误
你不能直接将lambda赋值给std::shared_ptr类型变量,std::shared_ptr是智能指针,需要托管堆上的实例对象,你需要先把lambda包装为std::function实例,再用std::shared_ptr托管该实例。
- 智能指针初始化逻辑错误
修正后的可运行代码
字段定义修正
std::shared_ptr<std::function<std::shared_ptr<MyClass>()>> myClassLazyLoader;
初始化逻辑修正
myClassLazyLoader = std::make_shared<std::function<std::shared_ptr<MyClass>()>>( [] { return std::make_shared<MyClass>(); } );
调用逻辑
你之前写的解引用调用写法本身是正确的,修正前两处错误后即可正常运行:
std::shared_ptr<MyClass> instance = (*myClassLazyLoader)();
方案优化建议
你的懒加载整体思路是可行的,但套两层std::shared_ptr的写法完全没有必要,除非你有特殊的共享加载器所有权的需求,否则可以直接简化为以下写法,性能更高且更容易维护:
// 直接用std::function作为成员变量,不需要套shared_ptr std::function<std::shared_ptr<MyClass>()> myClassLazyLoader; // 初始化直接赋值lambda即可 myClassLazyLoader = [] { return std::make_shared<MyClass>(); }; // 调用更简洁 std::shared_ptr<MyClass> instance = myClassLazyLoader();
如果需要支持加载器未初始化的空状态判断,也可以用std::optional包装std::function,不需要引入智能指针。
内容的提问来源于stack exchange,提问作者rombas
相关产品推荐
相关产品推荐

