条款21:必须返回对象时,别妄想返回其reference——120

返回reference可能指向一个销毁的local stack对象 ——120

考虑下列程序:

class Rational{
public:
    Rational(int numerator=0,
                int denominator=1);
    ...
private:
    int n,d;
    friend const Rational operator*(const Rational& lhs,
    const Rational& rhs);
};

如果定义一个local变量,就是在stack空间创建对象。将上面程序的operator* 函数写成如下:

const Rtional& operator* (const Rational& lhs, const Rational& rhs)
{
    Rational result(lhs.n*rhs.n,lhs.d*rhs.d);
    return result;
}

这样修改导致这样一个问题:首先你不免要调用Rational的构造函数,再者 result只是一个local stack变量,当调用函数结束时会被销毁,导致返回的reference指向一个空的对象。

返回reference指向一个Heap对象可能程序爱你内存泄漏——122

我们再将Rational中的operator* 函数改写成如下形式:

const Rational& operator*(const Rational& lhs, const Rational& rhs)
{
    Rational* result=new Rational(lhs.n*rhs.n,lhs.d*rhs.d);
    return *result:
}

这种改写仍然存在付出一个“构造函数调用”的代价,另者,你使用new动态分配内存,又怎么使用delete释放资源呢?这常常很困难完成。

返回reference指向static对象仍不可取——122

再次改写:

const Rational& operator* (const Rational& lhs,const Rational& rhs)
{
    static Rational result;
    result=...;
    return result;
}

这种写法像所有用上static对象的设计一样,这一个也立刻造成我们对多线程安全性的疑虑。再者,我们思考下列例子:

Rational a,b,c,d;
...
if((a*b)==(c*d)){
...
}
else{
...
}

毫不奇怪,表达式((a* b)==(c* d))总是为true。

一个“必须返回新对象”的函数的正确写法

inline const Rational operator* (const Rational& lhs,const Rational& rhs)
{
    return Rational(lhs.n*rhs.n,lhs.d*rhs.d);
}

总结——124

绝不要返回pointer或reference指向一个local stack对象,或返回reference指向一个heap-allocated对象,或返回pointer或reference指向一个local static对象而有可能同时需要多个这样的对象。条款4已经为“在单线程环境中合理返回reference指向一个local static对象”提供了一份设计实例。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值