何时将std :: reference_wrapper转换为T&?

oz1*_*1cz 5 c++ c++11 reference-wrapper

请考虑以下代码:

#include <iostream>
#include <functional>

using namespace std;

template<class T>
void fun(T t) 
{ 
    t+=8;
}


int main()
{
    int i = 0;
    fun(ref(i));
    cout << i << endl;
}
Run Code Online (Sandbox Code Playgroud)

此代码打印"8".我假设fun()中的t自动转换为int&.

但是,如果我取代t+=8t=8,程序将无法编译.

为什么?

eca*_*mur 4

reference_wrapper<T>有一个隐式转换运算符 to T &,因此它将转换为T &aT &比 a 更好的匹配reference_wrapper<T>

在增强赋值表达式中,唯一可行的运算符是int &operator+=(int &, int)soint &被提取。

在赋值表达式中,也可以使用成员运算符reference_wrapper<int>::operator=(const reference_wrapper<int> &),因此优先使用成员运算符;然后,编译器尝试从常量构造引用包装器8,但失败了。赋值运算符具有重新绑定的作用,这对于像tie预期那样工作的设施是必要的。

这意味着引用包装器比 C++ 引用更接近 Python 等语言中的引用:

#include <functional>
#include <iostream>

int main() {
    int i = 1, j = 2;
    std::ref(i) = j;
    std::cout << i << '\n';                 // prints '1'
}
Run Code Online (Sandbox Code Playgroud)