获取返回的临时对象的地址

Taking the address of a returned temporary object

我有一段我认为有效的 C++20 代码,但我们的静态分析器认为它不安全。

struct Foo {
  explicit Foo() { activeFoo = this; }
  ~Foo() { activeFoo = nullptr; }

  Foo(const Foo&) = delete;
  Foo(Foo&&) = delete;

  inline static const Foo* activeFoo = nullptr;
};

Foo makeFoo()
{
  // Is there a dangling reference here?
  return Foo();
}

int main()
{
  auto myFoo = makeFoo();
}

我的静态分析器认为 makeFoo 导致 activeFoo 指向一个临时对象,并将成为一个悬空指针。我认为这是错误的; return Foo(); 应该得到一个有保证的复制省略(如删除的复制和移动构造函数所证明的那样),因此只构造了一个 Foo 实例,myFoo.

谁是正确的?

makeFoo 和复制省略(正如您所指出的,自 C++17 起在这个特定示例中得到保证)甚至都不重要。

activeFoo 永远不能悬空。如果它在其生命周期结束后指向一个对象,那么该对象的析构函数会将 activeFoo 重置为 nullptr,这意味着它不能指向该对象,这是一个矛盾。这是假设为每个创建的 Foo 类型的对象调用析构函数。从技术上讲,如果您 placement-new 明确反对,情况可能并非总是如此,尽管它应该如此。

然而,我通常不希望静态分析器弄清楚这个逻辑。如果没有关于静态分析器的一些细节或它到底抱怨什么,就很难说更多了。