【问题标题】:Why is rval ref binding to lval ref function?为什么 rval ref 绑定到 lval ref 函数?
【发布时间】:2017-02-04 12:44:13
【问题描述】:

在下面的代码中,is_rvalue_reference 返回 true。 我希望调用testRef(int &&) 而不是testRef(int &),但事实并非如此(至少在我的Visual Studio 2015 编译器中)。

知道原因吗?

void testRef( int&& i )
{
    cout << "called testRef(int&&) " << endl;
}

void testRef( int& i )
{
    cout << "called testRef(int&) " << endl;
}

int main()
{
    int && rvalref = 4;
    cout << "is rval? : " << std::is_rvalue_reference<decltype( rvalref )>() << endl;
    testRef( rvalref );
}

请注意,这与Rvalue Reference is Treated as an Lvalue?中的问题不同

在那篇文章中,他们谈论的是函数内部的变量:这就像在我的示例中询问变量 i 是右值还是左值(答案是它在两者中都是左值情况下,因为它在两种情况下都有地址)。

拥有右值和std::move(它是对右值的强制转换)的全部意义在于允许在函数和构造函数中选择正确的重载。 例如,以下两种情况都会调用testRef(int &amp;&amp; i)

int main()
{
  int g = 3;
  testRef(std::move(g));
  testRef(4);
}

但是对于右值引用,情况似乎并非如此。

【问题讨论】:

  • 你可以使用一些简化的规则:如果 var 有一个名字 - 它是一个左值
  • rvalref 是一个左值。 decltype(identifier) 的结果可能与由该标识符组成的表达式的值类别不同
  • 您链接到的问题的答案也回答了您的问题,尽管它是一个略有不同的问题

标签: c++ c++11 reference-binding


【解决方案1】:

rvalref 是对象的标识符。对象的标识符始终是左值。

表达式永远没有引用类型。表达式rvalref 具有类型int 和值类别“左值”。

在声明int &amp;&amp; rvalref 中,&amp;&amp; 描述了rvalref 将如何被初始化(即通过向另一个表达式表示的对象添加一个新名称,而不是创建一个新对象),仅此而已。

在表达式中,对象名称的行为是相同的,无论该名称是否是该对象的第一个名称。

decltype(general_expression) 相比,代码decltype(identifier) 具有特殊行为。它没有给出由该标识符组成的表达式的类型和值类别。代码decltype((identifier)) 可以做到这一点。 Further reading

【讨论】:

    猜你喜欢
    • 2020-11-10
    • 2014-09-21
    • 2017-10-20
    • 1970-01-01
    • 1970-01-01
    • 2011-02-21
    • 2021-10-18
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多