有没有相当于shared_from_this的weak_ptr

Is there a weak_ptr equivalent to shared_from_this?

本文关键字:weak ptr this from 相当于 shared 有没有      更新时间:2023-10-16

我有一个类,我知道它将永远std::shared_ptr拥有。但是,将shared_ptr甚至weak_ptr传递给不需要所有权或生存期保证的函数和方法会产生不必要的开销。为了解决这个问题,我经常将原始指针传递给函数。类本身继承自std::enable_shared_from_this因此,如果函数需要获取指针的所有权,则可以使用该类的方法获取shared_ptr

这一切都运行良好。但是,在某些情况下,我真的不想从原始指针中制作shared_ptr,而是我想要的是weak_ptr

根据我对std::shared_ptr通常实现的理解,它有两个原子变量用作参考计数器; 一个用于shared_ptr,一个用于weak_ptr

如果我只有一个指向我的类的原始指针,并且我想要一个weak_ptr,我必须首先创建一个shared_ptr并转换它。这样做意味着引用计数器将像这样更改:

  • 构造shared_ptr、递增shared_ptr计数器
  • 复制构造weak_ptr,递增weak_ptr计数器
  • 允许shared_ptr超出范围,减少计数器shared_ptr

这似乎违背了"你不为不使用的东西付费"的想法。有没有办法让我的类只提供weak_ptr而不先创建shared_ptr

提案

P0033 在 2015 年 10 月的会议上被 C++17 接受,该提案增加了从std::enable_shared_from_this派生的类weak_from_this

有没有办法让我的班级只提供weak_ptr而不先创建shared_ptr?

不是在 C++14 中;enable_shared_from_this支持的唯一操作是创建shared_ptr。现在,enable_shared_from_this应该有足够的信息来直接构建weak_ptr。但是你不能从外部做到这一点,因为该类不会向你公开其实现细节。

C++17 支持通过 weak_from_thisenable_shared_from_this类获取weak_ptr

实现起来几乎是微不足道的,不值得放在库中......

#include <memory>
template<class T> std::weak_ptr<T> weak_from_this(T*p) {
  return { p->shared_from_this() };
}
struct S : std::enable_shared_from_this<S>
{
  auto foo() {
    return weak_from_this(this);
  }
};

int main()
{
  auto ps = std::make_shared<S>();
  auto wps = ps->foo();
}