dynamic_cast和右值参考

时间:2016-01-20 13:17:59

标签: c++ c++11 language-lawyer dynamic-cast rvalue

class A{
public:
    virtual ~A() {};
};

class B : public A{ };

int main(){

    A&& p = B();

    dynamic_cast<B&&>(std::move(p));

}

引发错误(g ++ 5.2.0):

error: conversion to non-const reference type 'std::remove_reference<A&>::type& {aka class A&}' from rvalue of type 'A' [-fpermissive]

它会尝试将std::move(p)转换为A&类型,但我无法弄清楚原因。在转换为右值引用之前,我认为有必要将p转换为右值,但如果我删除std::move则编译正常。来自cppreference

  

dynamic_cast < new_type > ( expression )

     

与其他演员表达式类似,结果是:

     

如果new_type是左值引用类型(表达式必须是左值),则为左值

     

如果new_type是右值引用类型(表达式可能是左值或右值),则为xvalue

甚至是N3337的5.2.7:

  

dynamic_cast<T>(v)

     

如果T是指针类型,则v应该是指向完成类类型的指针的prvalue,结果是类型T的prvalue。如果T是左值引用类型,则v应该是完整类的左值类型,结果是由T引用的类型的左值。如果T是右值引用类型,则v应该是具有完整类类型的表达式,结果是由类型引用的类型的x值。 Ť

唯一的要求是我使用完整的类类型std::move(p),不是吗?

2 个答案:

答案 0 :(得分:6)

您的代码当然没问题:

  

如果T是右值引用类型,则v应为具有a的表达式   完整的类类型,结果是引用类型的xvalue   到T

据推测,当引入右值引用时,dynamic_cast没有正确更新,并且仍然强制执行前C ++ 11规则,即rvalues只能绑定到const左值引用(请注意它在将目标类型更改为B const&&时甚至不起作用,尽管错误消息暗示了这一点!)。

归档为#69390

答案 1 :(得分:2)

这似乎有效:

B&& b = std::move(dynamic_cast<B&>(p));

不能告诉你为什么你的不正确。