【问题标题】:static_cast dangling reference when downcasting [duplicate]向下转换时的static_cast悬空引用[重复]
【发布时间】:2018-11-28 11:37:37
【问题描述】:

以下代码是否正确或是否由于悬空引用而产生未定义的行为以及为什么它完全正确:

class A {};
class B : public A {};

B& f(A& a) {
  // Dangling reference here?
  return static_cast<B&>(a);    
}

int main()
{
  A a;
  B& b = f(a);
}

【问题讨论】:

  • @Incomputable 我仔细检查过,我认为您的“可能重复”是正确的。
  • 你没有创建任何临时对象,所以这里什么都没有
  • a 都指向同一个对象,其生命周期在离开main 时结束。 b 指的是a 的一个子对象,它的生命周期也在离开main 时结束。所以没有悬空的参考。
  • 我查看了static_cast的文档。 downcast 在这种情况下究竟是什么意思?

标签: c++ c++11 language-lawyer


【解决方案1】:

这是未定义的行为,但不是因为悬空引用。使用static_cast 将对象从父类转换为子类的行为实际上不是子类是未定义的行为:

 B& b = f(a); // Casts `A` type to `B` incorrectly

参见相关标准报价here

【讨论】:

    【解决方案2】:

    悬空引用是对不再存在的对象的引用。 在您的代码示例中,没有问题,因为 A 与 B 存在于同一范围内,因此引用始终有效。

    现在,以这个修改后的示例为例,在创建对象 A 的引用后删除它。这实际上是一个悬空引用,在对象 A 被删除后会产生未定义的行为。

    #include <iostream>
    
    class A {
    public:
      int m;
    };
    class B : public A {};
    
    B& f(A& a) {
      return static_cast<B&>(a);
    }
    
    int main()
    {
      A *a = new A();
      a->m = 42;
      B& b = f(*a);
      std::cout << b.m << std::endl; // Valid                                       
      delete a; // Dangling reference created here                                
      std::cout << b.m << std::endl; // Undefined behavior                          
    }
    

    【讨论】:

    • 你能提供一些来源吗?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-09-13
    • 2018-02-28
    • 1970-01-01
    • 2013-05-03
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多