简单的结论:
左值:在内存中占有地址。
右值:在内存中没占用地址。
简单的例子
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
int main()
{
// value就是一个左值,10就是一个右值
int value = 10;
// value + 10是一个右值
value + 10 = 10;
// 10是一个右值
10 = value;
}
在没有引用或指针的情况下,函数的返回值是一个右值。
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
int global_val = 100;
int get_value()
{
return global_val;
}
int main()
{
int value = get_value();
// 错误get_value()是一个右值,不占有地址
get_value() = 100;
}
含有引用或指针的话,函数的返回值为左值。
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
int global_val = 100;
int* get_value()
{
return &global_val;
}
int& get_value2()
{
return global_val;
}
int main()
{
int* value = get_value();
// 正确,get_value()的返回值为指针,可以进行赋值
*get_value() = 1000;
cout<<global_val<<endl;
// 正确,get_value2()的返回值为引用,可以进行赋值
get_value2() = 2000;
}
C++函数返回左值的功能十分常用,比如[]运算符的重载,返回值就是一个左值,可以进行赋值。
#include <iostream>
#include <map>
#include <algorithm>
using namespace std;
int main()
{
map<int,int> mnn_con;
mnn_con[0] = 10;
}
左值、右值间的相互转换
左值可以转为右值,右值不能转为左值
#include <iostream>
#include <map>
#include <algorithm>
using namespace std;
int main()
{
int a = 10;
int b = 10;
int c = a + b;
}
a,b为左值,但在 c = a + b时,a,b变为了右值。
&运算符
&接收一个左值,将左值变为右值
#include <iostream>
#include <map>
#include <algorithm>
using namespace std;
int main()
{
int a = 10;
// a是一个左值,&a变为一个右值
int* b = &a;
}
非const左值引用不能被赋右值。
#include <iostream>
#include <map>
#include <algorithm>
using namespace std;
int main()
{
// 错误,非const修饰的引用不能被赋右值
int& a = 10;
// 正确,const左值引用可以被赋右值
const int& b = 20;
}