首页 > 后端开发 > C++ > 尽管处理可变大小的 Lambda 表达式,std::function 如何保持固定大小?

尽管处理可变大小的 Lambda 表达式,std::function 如何保持固定大小?

Mary-Kate Olsen
发布: 2024-12-04 17:01:15
原创
634 人浏览过

How Does std::function Maintain a Fixed Size Despite Handling Variable-Sized Lambda Expressions?

探索 std::function 的实现

在 lambda 表达式的世界中,大小的概念变得流动,因为它们是本质上包装在具有可变大小引用的类中。然而,std::function 需要固定的大小。这就引出了一个问题:这是如何协调的?

答案在于类型擦除。让我们设想一个简化的实现:

struct callable_base {
   virtual int operator()(double d) = 0;
   virtual ~callable_base() {}
};
template <typename F>
struct callable : callable_base {
   F functor;
   callable(F functor) : functor(functor) {}
   virtual int operator()(double d) { return functor(d); }
};
class function_int_double {
   std::unique_ptr<callable_base> c;
public:
   template <typename F>
   function(F f) {
      c.reset(new callable<F>(f));
   }
   int operator()(double d) { return c(d); }
};
登录后复制

在这种简单的方法中,std::function 存储指向基类的唯一指针。对于每个不同的函子,都会创建一个派生类型并动态实例化。因此,std::function 的大小保持不变,同时在堆上容纳一系列函子。

优化技术进一步完善了该方案,使用小对象优化、避免间接等。然而,从概念上讲,核心思想保持不变。

关于 std::function 的副本,实验证据表明可调用对象的独立副本。一个人为的示例:

int main() {
   int value = 5;
   typedef std::function<void()> fun;
   fun f1 = [=]() mutable { std::cout << value++ << '\n' };
   fun f2 = f1;
   f1(); // prints 5
   fun f3 = f1;
   f2(); // prints 5
   f3(); // prints 6 (copy after first increment)
}
登录后复制

输出表示隔离副本而不是共享状态,因为不同的调用独立地增加值。

以上是尽管处理可变大小的 Lambda 表达式,std::function 如何保持固定大小?的详细内容。更多信息请关注PHP中文网其他相关文章!

来源:php.cn
本站声明
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
作者最新文章
热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板