时间:2014.03.11
地点:基地二楼
----------------------------------------------------------------------------
一、简述
正如我们所见的,++和 -- 都存在前置和后置两种形式,我们的记忆里的规则是:前置累加后取出,后置是取出后累加。我们来看定义,看它为什么会存在这种区别。
//前置式,累加后取出 UPInt& UPInt::operator++() { *this+=1; //累加 return *this; //取出 }
//后置式,取出后累加 const UPInt upInt::operator++(int) { UPInt oldVlaue=*this; //取出 ++(*this); //累加 return oldVlaue; }
----------------------------------------------------------------------------
二、为什么
为什么前置和后置在定义上会有区别,这种区别将导致什么样的结果,这是下面将要讨论的。
首先看为什么后置式返回一个const对象?反证法:假如这样,那么下面程序是合法的:
UPInt i; i++++; //执行后置调用两次上述代码等效于
i.operator++(0).operator++(0);operator++的第二次调用动作实行于第一次调用动作返回的对象上。这并不是我们想要的,因为:一、它和内建类型的行为不一致。设计类的至上原则就是看int类型行为如何并遵循。显然int类型是不支持连续两次使用后置式操作的。二、如果我们去掉const,使得上述行为合法,但显然第二个operator++所改变的对象时第一个operator++返回的对象,而并非原对象,原对象还是只被增加了一次,这会使得违背你看起来加两次的意愿,引起混淆,所以干脆禁用。加上const后第一次调用operator++返回一个const对象,而此时连续再次operator++时将在这个const上执行,依据定义显然是非法的。如果有时你困惑于函数返回const对象是否合理,那么这里便是一个很好的例子。
另外是关于效率问题,后置式函数会产生一个临时对象,作为返回值之用。比如上面的oldValue,需要构造和析构,而前置式不会出现这种情况。所以说前置式天生效率高。