cppreference.com
, .
& ()
|
(1) | ||||||||
&& ()
|
(2) | ( C++11) | |||||||
1) :
S& D; D, , -- S.2) :
S&& D; D, , -- S.| , ( ) | ||
| ( C++11) |
( cv-) void .
cv ; , , typedef, decltype, ( C++11) , .
; , , , ( - , , ).
, , , :
int& a[3]; //
int&* p; //
int& &r; //
|
typedef, : , : typedef int& lref;
typedef int&& rref;
int n;
lref& r1 = n; // r1, int&
lref&& r2 = n; // r2, int&
rref& r3 = n; // r3, int&
rref&& r4 = 1; // r4, int&&
( , |
( C++11) |
( cv ):
#include <iostream>
#include <string>
int main() {
std::string s = "";
std::string& r1 = s;
const std::string& r2 = s;
r1 += ""; // s
// r2 += "!"; // :
std::cout << r2 << '\n'; // s, ""
}
:
#include <iostream>
#include <string>
void double_string(std::string& s) {
s += s; // 's' , 'str' main()
}
int main() {
std::string str = "";
double_string(str);
std::cout << str << '\n';
}
lvalue, lvalue:
#include <iostream>
#include <string>
char& char_number(std::string& s, std::size_t n) {
return s.at(n); // string::at()
}
int main() {
std::string str = "";
char_number(str, 1) = ''; // lvalue,
std::cout << str << '\n';
}
#include <iostream>
#include <string>
int main() {
std::string s1 = "";
// std::string&& r1 = s1; // : lvalue
const std::string& r2 = s1 + s1; // : lvalue
//
// r2 += ""; // :
//
std::string&& r3 = s1 + s1; // : rvalue
r3 += ""; // :
//
std::cout << r3 << '\n';
}
, rvalue lvalue, rvalue rvalue ( prvalue xvalue), lvalue lvalue: #include <iostream>
#include <utility>
void f(int& x) {
std::cout << " lvalue f(" << x << ")\n";
}
void f(const int& x) {
std::cout << " lvalue f(" << x << ")\n";
}
void f(int&& x) {
std::cout << " rvalue f(" << x << ")\n";
}
int main() {
int i = 1;
const int ci = 2;
f(i); // f(int&)
f(ci); // f(const int&)
f(3); // f(int&&)
// f(const int&), f(int&&)
f(std::move(i)); // f(int&&)
// rvalue lvalue,
//
int&& x = 1;
f(x); // f(int& x)
f(std::move(x)); // f(int&& x)
}
, , , , ( std::vector::push_back()), . rvalue xvalue, : int i2 = 42;
int&& rri = std::move(i2); // i2
, : std::vector<int> v{1,2,3,4,5};
std::vector<int> v2(std::move(v)); // rvalue v
assert(v.empty());
|
( C++11) |
|
, , , std::forward. , : template<class T>
int f(T&& x) { // x,
return g(std::forward<T>(x)); //
}
int main() {
int i;
f(i); // , lvalue, f<int&>(int&), std::forward<int&>(x),
// lvalue
f(0); // , rvalue, f<int>(int&&), std::forward<int>(x),
// rvalue
}
template<class T>
int g(const T&& x); // x, : const T
// cv-
template<class T> struct A {
template<class U>
A(T&& x, U&& y, int* p); // x, : T
// ,
// y
};
2)
auto&&, , :auto&& vec = foo(); // foo() lvalue rvalue, vec
//
auto i = std::begin(vec); //
(*i)++; //
g(std::forward<decltype(vec)>(vec)); // ,
for (auto&& x: f()) {
// x ;
//
//
}
auto&& z = {1, 2, 3}; // ** (
// )
|
( C++11) |
std::string& f()
{
std::string s = "";
return s; // s:
//
}
std::string& r = f(); //
std::cout << r; // :
std::string s = f(); // :
//
__cpp_rvalue_references |
200610L |
(C++11) |
C++:
| CWG 1510 | C++11 | cv- decltype
|
|
| CWG 2550 | C++98 | void
|
| Thomas Becker, 2013 - Rvalue C++ |