OOP-THU
OOP-THU copied to clipboard
std::forward介绍(补充参数转发知识)
课上讲过实现左值与右值转发的一个工具——std::move,我这边想介绍一下实现完美转发的工具,std::forward。
Note: 所谓“完美转发”是指把参数“原封不动”传给函数。若参数是右值,则参数转为右值;若参数是左值,则传为左值。这样保证了不会丢失参数原本性质。这个方法面向与解决不必要的拷贝函数调用,同时也提高了程序效率。
std::forward 则解决了完美转发提出的问题。与std::move相比,它的目的是保持参数原本形式,不能从左值换成右值。它在
- template <class T> T&& forward (typename remove_reference<T>::type& arg) noexcept;
- template <class T> T&& forward (typename remove_reference<T>::type&& arg) noexcept;_ 这样std::forward根据接收参数的实际类型来判断传右值或者左值。何况,返回类型是引用,因此保证了转发中不能复制参数。
使用例子如下:
#include <utility>
#include <iostream>
void checkVal(const int& x) { //左值转移
std::cout << "[lvalue]";
}
void checkVal(int&& x) { //右值转移
std::cout << "[rvalue]";
}
template <class T>
void func (T&& x) {// 无论传给右值还是左值,都对函数里面构造临时对象x,x 总是 左值
checkVal(x);
checkVal(std::forward<T>(x)); //根据参数实际情况转移左值或右值
}
int main () {
int a;
std::cout << "calling func with lvalue: ";
fn (a);
std::cout << std::endl;
std::cout << "calling func with rvalue: ";
fn (0);
std::cout << std::endl;
return 0;
}
输出: calling func with lvalue: [lvalue][lvalue] calling func with rvalue: [lvalue][rvalue]
因此,std::forward 实现了完美转发原理,在传参数中保留了参数原本性质,也避免了传右值时调用拷贝函数,从此提高了程序的效率。
std::forward重点 stdForward.pptx
OK