右值从哪里来?

Where is the rvalue coming from?

我了解引用和值类别,因为后者在一些 C++ 错误中被提及。

我有一个函数 referenceToDouble 接收对 double 的引用。通过观察 this video on value categories,我相信下面的 leftright 是对 double.

左值引用

main 中,当我创建类型为 double 的变量 ab 时,我没有收到错误。下面的代码显示 ab 类型 float 这给了我一个错误。

#include <cassert>

double referenceToDouble(double& left, double& right) {
    if (left >= right) {
        right = left;
    }
    else {
        left = right;
    }

    return left;
}

int main() {
    float a = 55.5;
    float b = 55.5;

    assert(55.5 == referenceToDouble(a, b));
}

当我将 ab 的数据类型切换为 float 时,出现此错误。

checkReferences.cpp: In function 'int main()':
checkReferences.cpp:18:35: error: cannot bind non-const lvalue reference of type 'double&' to an rvalue of type 'double'
   18 |  assert(55.5 == referenceToDouble(a, b));
      |                                   ^
checkReferences.cpp:3:34: note:   initializing argument 1 of 'double referenceToDouble(double&, double&)'
    3 | double referenceToDouble(double& left, double& right) {
      |                          ~~~~~~~~^~~~

我的问题是:

  • 右值从哪里来?

  • 是否有包含adouble值的临时变量 那是从 float 投射出来的?这是临时的然后 rvalue?

  • 或者是引用 55.5 的错误,它是一个文字和 因此是右值?

  • 这里不涉及return类型吗?我想不是因为这个 是 return 按值而不是按引用。

我试过reading the answer to this question也有类似的错误,但还是没能打消疑虑。我也认为我知道解决方案(使用 double)是什么,但我试图了解引擎盖下发生的事情。

Is there a temporary variable that contains the double value of a that was cast from float? And is this temporary then the rvalue?

是的。类型为 double&leftright 无法直接绑定到 float。它们必须首先转换为 doubles,它们是临时值(右值)并且不能绑定到对非常量的左值引用。

如果您将 leftright 的类型更改为 const double& 那么它将正常工作。转换后的 double 临时值(右值)可以绑定到 const.

的左值引用