C++Primer学习-类(隐含的this指针)

        成员函数具有一个附加的隐含形参,即指向该类对象的一个指针。这个隐含形参命名为this,与调用成员函数的对象绑定在一起。成员函数不能定义this形参,而是编译器隐含地定义。成员函数可以显式的使用this,但不是必须这么做。

1.何时使用this

   必须显式使用this指针:当需要将一个对象作为整体引用而不是引用对象一个成员时。

myScreen.move(4, 0).set('#');
//等价于
myScreen.move(4, 0);
myScreen.set('#');

2.返回*this

在单个表达式中调用move和set操作时,每个操作必须返回一个引用,该引用指向执行操作的那个对象:

class Screen
{
   public:
       Screen &move(index r, index c);
       Screen &set(char);
       Screen &set(index, index, char);
};

这样,每个函数都返回调用自己的那个对象。使用this指针可以访问该对象:

Screen &Screen::set(char c)
{
   contents[cursor] = c;
   return *this;
}
Screen &Screen::move(index r, index c)
{
    index row = r * width;
    cursor = row + c;
    return *this;
}

3.从const成员返回*this

在普通的非const成员函数中,this的类型是一个指向类类型的const指针。可以改变this所指向的值,但不能改变this所保存的地址。在const成员函数中,this的类型是一个指向const类类型对象的const指针。既不能改变this所指向的对象,也不能改变this所保存的地址。
   不能从const成员函数返回指向类对象的普通引用。const成员函数只能返回*this作为一个const引用。

给Screen增加一个const成员函数:display操作。将display作为Screen的const成员,则display内部的this将是一个const Screen*型的const:

myScreen.move(4,0).set('#').display(cout);  //OK  
myScreen.display().set('*');    //Error
问题在于这个表达式是在由display返回的对象上运行set。该对象是const,因为display将其对象作为const返回。不能在const对象上调用set。

4.基于const的重载

解决以上问题,我们定义两个display操作:一个是const,一个不是const。基于成员函数是否为const,可以重载一个成员函数;同样,基于一个指针形参是否指向const,也可以重载一个函数。

01.class Screen  
02.{  
03.public:  
04.    //As before  
05.  
06.    Screen &display(std::ostream &os)  
07.    {  
08.        do_display(os);  
09.        return *this;  
10.    }  
11.    const Screen &display(std::ostream &os) const  
12.    {  
13.        do_display(os);  
14.        return *this;  
15.    }  
16.  
17.private:  
18.    void do_display(std::ostream &os) const  
19.    {  
20.        os << contents;  
21.    }  
22.    //As before  
23.};  


调用:

01.Screen myScreen(5,3);  
02.const Screen blank(5,3);  
03.myScreen.set('#').display(cout);    //调用非const版本  
04.blank.display(cout);                //调用const版本 


5.可变数据成员

可以通过将它们声明为mutable来实现:类的数据成员(甚至是在const成员函数中)可以修改。

可变数据成员永远都不能为const,甚至当它们是const对象的成员时也如此。因此,const成员函数可以改变mutable成员。

01.class Screen  
02.{  
03.public:  
04.    //...  
05.  
06.private:  
07.    mutable size_t access_ctr;  
08.  
09.    //使用access_ctr来跟踪Screen成员函数的调用频度  
10.    void do_display(std::ostream &os) const  
11.    {  
12.        ++ access_ctr;      //OK  
13.        os << contents;  
14.    }  
15.};


【建议:用于公共代码的私有实用函数】
使用私有实用函数好处:

1)避免在多个地方编写同样的代码

2)当涉及到的动作变得更复杂时,只在一处而不是两处编写这些动作有更显著的意义。

3)希望在开发时增加调试信息,如果只需要改变一个定义来增加或删除调试代码,这样更容易。

4)这个额外的函数调用不需要涉及任何开销。


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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值