一篇有助于理解C指针的文章
左值和右值
- C++的表达式要不然是右值(rvalue,读作"are-value"),要不然就是左值(lvalue,读作"ell-valule")。这两个名次是从C语言继承过来的,原本就是为了帮助记忆的:左值可以位于赋值语句的左侧,右值不能。
- 在C++语言中,二者的区别就没有那么简单了。一个左值表达式的求值结果是一个对象或者一个函数,然而以常量对象为代表的某些左值实际上不能作为赋值语句的左侧运算对象。此外,虽然某些表达式的求值结果是对象,但它们是右值而非左值。可以做一个简单的归纳:当一个对象被用作右值的时候,用的是对象的值(内容);当对象被用作左值的时候,用的是对象的身份(在内存中的位置)。
- 不同的运算符对运算对象的要求各有不同,有的需要左值运算对象、有的需要右值运算对象;返回值也有差异,有的得到左值结果、有的得到右值的结果。一个重要的原则是在需要右值的地方可以用左值来代替,但是不能把右值当成左值(也就是位置)使用。当一个左值被当成右值使用时,实际使用的是它的内容(值)。常见地,运算符要用到左值的有一下几个:
- 赋值运算符(*)需要一个(非常量)左值作为其左侧运算符对象,得到的结果也仍然是一个左值;
- 取地址符(&)作用于一个左值元算对象,返回一个指向该运算对象的指针,这个指针是一个右值。
- 内置解析引用运算符、下标运算符、迭代器解析引用运算符、
string
和vector
的下标运算符的求值结果都是左值。 - 内置类型和迭代器的递增递减运算符作用于左值运算对象,其前置版本所得的结果也是左值。