zoukankan      html  css  js  c++  java
  • 条款21 :必须返回对象时,别妄想返回其reference

    上一条款我们说了,能以pass by reference to const 尽量不用pass by value。是不是所有的都要这样呢?

    这会使我们犯错:开始传递一些reference指向其实并不存在的对象,这不是一件好事。

    考虑一个用以表现有理数的class,内含一个函数用来计算两个有理数的乘积。

    classRational{

    public:

           Rational(intnumerator=0

                                intdenominator=-1);

           ...

    private:

           intn,d;

           friendRationaloperator*(constRational&lhs,constRational&rhs);

    };

    这里有版本是一个pass by value的。但是我们想能不能在函数返回时,pass by reference to const?

    我们还知道,reference是一个已经存在的对象的引用。所以我们要创建一个对象,我们也知道创建一个对象可以在栈上,或堆上创建。以下版本是一个在栈上创建的。

    constRational&operator*(constRational&lhs,constRational&rhs){

           Rationalresult(lhs.n*rhs.n,lhs.d*rhs.d);

           returnresult;

    }

    我们想在返回时,传出一个引用。这个引用指向了栈中的result。问题出来了,当函数结束时,会调用Rational的析构函数,那么result对象会被销毁。那传出去的reference是什么呢。不知道~~~~

     

    如果在栈上创建,不可以的话,我们是不是可以在堆上创建?下面的版本是在堆上创建。

    constRational&operator*(constRational&lhs,constRational&rhs){

           Rational*result  =newRational(lhs.n*rhs.n,lhs.d*rhs.d);

           returnresult;

    }

    现在的问题来了,我们依然要构造一个新对象。还不至如此,我们发现,我们new了,还没有做delete呢。那在哪里delete呢。我们没有办法~~~~~~~~~~

    因此,考虑到这些,我们会想在堆和栈上都无法完成,如果我们在static上面呢?很好的想法,不过更加失败。

    constRational&operator*(constRational&lhs,constRational&rhs){

           staticRationalresult;      

           result->n=lhs.n*rhs.n;   result->d=lhs.d*rhs.d

           returnresult;

    }

    就像所有用static对象的设计一样,这一个也立刻会造成我们对多线程的安全性的疑虑。不过那些还是显而易见的,如果想看更加深层次的,请看下面代码:

    booloperator==(constRatioal&lhs,constRational&rhs){

           Rationala,b,c,d;

           ...

           if((a*b)==(c*d)){

                  ...

           }else{

                  ...

           }

    }

    你猜怎么样?(a*b)==(c*d)全部都是true。

    注意在operator==作用之前,先是两个operator*起作用。还要注意每一次调用operator*都返回的是对一个static对象的引用。每一次调用的确也改变了static对象的值,但是由于是返回的reference,也就是指针。所以当两次调用后,再调用operator==时,你就会发现所指同一个static东西,且相等。

     

    请记住:

           绝对不要返回pointer或reference指向一个local stack , 或 heap-allocated对象,或返回一个local static对象。

  • 相关阅读:
    在intellij 下用java spring + Mysql + Hibernate 开发的第一个数据库demo
    推荐一个找到一个比较好的spring,java学习教程
    ReactiveCocoa 中signal(operation) then与doNext的区别
    grunt
    Swiper.js wap app 图片滑动效果
    less 路径 写法
    html5 input placeholder 占位符 输入框提示文本
    js 大小写转换
    css 修改选中文字的颜色
    keydown keypress keyup textInput
  • 原文地址:https://www.cnblogs.com/loveyakamoz/p/2772411.html
Copyright © 2011-2022 走看看