int & &
折叠为int&
int & &&
折叠为int&
int && &
折叠为int&
int && &&
折叠为int &&
move原理
namespace whz {
template<typename T>
struct remove_reference {
typedef T type;
};
template<typename T>
struct remove_reference<T&> {
typedef T type;
};
template<typename T>
struct remove_reference<T&&> {
typedef T type;
};
template<typename T>
typename remove_reference<_Tp>::type&& move(T &&t) {
typedef typename whz::remove_reference<T>::type ty;
return static_cast<ty &&>(t);
}
}
forward完美转发
std::forward被称为完美转发,它的作用是保持原来的值属性不变。
啥意思呢?通俗的讲就是,如果原来的值是左值,经std::forward处理后该值还是左值;如果原来的值是右值,经std::forward处理后它还是右值。
ps.完美转发要与通用引用模板配合使用
template<typename T>
void print(T &t) {
std::cout << "左值" << std::endl;
}
template<typename T>
void print(T &&t) {
std::cout << "右值" << std::endl;
}
template <typename T>
T&& forward(typename std::remove_reference<T>::type& param)
{
std::cout << "&" << std::endl;
return static_cast<T&&>(param);
}
template <typename T>
T&& forward(typename std::remove_reference<T>::type&& param)
{
std::cout << "&&" << std::endl;
return static_cast<T&&>(param);
}
template<typename T>
void testForward(T &&v) { // 配合通用引用
print(v);
print(::forward<T>(v));
print(std::move(v));
}
右值引用是左值
这也是为什么需要完美转发,你写一个wrapper去做一个静态代理,原本可能传入形参的是右值,但是你将这个右值传入wrapper方法后,变成了右值引用,右值引用是左值,你再将这个引用传入原方法就出问题了。