快速业务通道

C++中关于左值和右值的讨论

作者 佚名技术 来源 程序设计 浏览 发布时间 2012-06-29
是一个类型T的左值表达式。

Ex2.4
struct base{ //polymorphic type
int i;
virtual f() { }// do nothing;
};

struct derived: base {
};

derived d;
base b;
dynamic_cast<base&>(d).i=1; // dynamic_cast yields an lvalue of type base.
dynamic_cast<base>(d); //yields an rvalue of type base.
static_cast<base&>(d).i=1; //

( (base&)d ).i=1;

2.4

对于member selection表达式E1.E2,C++则比C要复杂的多。

A)如果E2表达式类型是T&,那么表达式E1.E2也是一个T的左值表达式。

B)如果E2不是引用类型的话,但是一个类型T的static 成员(data/function member),那么E1.E2也将是一个T的左值表达式,因为E1.E2实际上引用到的是一个static成员,该成员的存在与否与E1的左值性没有关系。

C)如果E1是左值,且E2是数据成员(data member),那么E1.E2 是左值,引用到E1所代表的对象的相应的数据成员。

Ex2.5

struct A{
public:

static int si;
static void sf();

int i;
void f();
int & ri;
};

extern A a;

A g();

void test()
{
void (*pf1)()=&a.sf; //a.sf is an lvalue of function type, refers to A::sf.
void (*pf2)()=&a.f; //error. a.f is not an lvalue and types mismatch.

g().ri=1; //ok. g().ri is a modifiable lvalue, though g() is an rvalue.
g().si=1; //ok. Refers to A::si;
g().i=1; //error. g().i is an rvalue.

a.i=1; //ok. a is an lvalue.

}

对于E1->E2,则可以看成(*E1)。E2再用上述方式来判断。

对于表达式E1.*E2, 在E1是左值和E2是一个指向数据成员的指针的条件下,该表达式是左值。

对于E1->*E2,可以看作(*E1)。*E2.在E2是一个指向数据成员的指针的条件下,该表达式是左值。

2.5 与C相比,C++中前缀++/——表达式、赋值表达式都返回左值。

逗号表达式的第二个操作数如果是左值表达式的话,逗号表达式也是左值表达式。

条件表达式(? :)中,如果第2和第3个操作数具有相同类型,那么该条件表达式的结果也是左值的。

Ex2.6

int i,j;
int & ri=i;
int* pi=&(i=1); //ok, i=1 is an modifiable lvalue referring to i;
++++i; //ok. But maybe issues undefined behavior because of the constraints
//about sequence points.

(i=2, j) =1; //ok
( ( I==1 ) ? ri : j ) = 0; //ok

需要当心的是,因为这种修改,在C中well-formed的代码,在C++中可能会产生未定义行为;另一方面会造成在C/C++中即使都是well-formed的代码,也会产生不同的行为。

Ex2.7
int i, j;
i=j=1; //well formed in C, maybe undefined in C++.

char array[100];
sizeof(0, array);

在C中,sizeof(0, array) == sizeof(char*)。而在C++中,sizeof(0, array)== 100;

2.6

typeid表达式总是左值的。

2.7

C++中需要左值的场合:

1) 赋值表达式中的左操作数,需要可修改的左值;

2) 自增/减中的操作数;

3) 取址运算中的操作数,需要左值(对象类型,或者函数类型),或者qualified id.

4) 对于重载的操作符来说,因为执行的是函数的语义,该操作符对于操作数的左值性要求、该操作符表达式的类型和左值性, 均由其函数声明决定。

2.8

左值性对程序行为的影响:

2.8.1

表达式的左值性对于程序的行为有重要的影响。如果一个需要(可修改)左值的场合,而没有对应的符合要求的左值,程序将是ill-formed;反之,如果需要一个右值的话,那么一个左值表达式就需要通过lvalue-to-rvalue conversion,转换为一个右值。

一个需要左值,或仅仅需要表达式的静态类型信息,而不关心表达式的左值性的场合,则往往抑制了在

凌众科技专业提供服务器租用、服务器托管、企业邮局、虚拟主机等服务,公司网站:http://www.lingzhong.cn 为了给广大客户了解更多的技术信息,本技术文章收集来源于网络,凌众科技尊重文章作者的版权,如果有涉及你的版权有必要删除你的文章,请和我们联系。以上信息与文章正文是不可分割的一部分,如果您要转载本文章,请保留以上信息,谢谢!

分享到: 更多

Copyright ©1999-2011 厦门凌众科技有限公司 厦门优通互联科技开发有限公司 All rights reserved

地址(ADD):厦门软件园二期望海路63号701E(东南融通旁) 邮编(ZIP):361008

电话:0592-5908028 传真:0592-5908039 咨询信箱:web@lingzhong.cn 咨询OICQ:173723134

《中华人民共和国增值电信业务经营许可证》闽B2-20100024  ICP备案:闽ICP备05037997号