Tsai笔记:Effective C++(2)—— 尽可能使用const

一、指针与const

  • 容易混淆的几个const指针
    const int p;                      //常变量
    const int* p;                     //数据是不可变,指针可变
    int const* p;                     //数据是不可变,指针可变
    int * const p;                    //指针是不可变,数据可变
    const int * const p;              //指针是不可变,数据不可变
    int const * const p;              //指针是不可变,数据不可变
    

二、迭代器与const

  • 迭代器常量:迭代器在功能上相当于指向某类型T的指针 T*,使用const iterator相当于定义一个迭代器为一个常量(T* const)
    const std::vector<int>::iterator it = v.begin(); //注意,此声明只表示迭代器本身是常量        
    *it = 10;                                        //编译通过,迭代器是常量,但数据可以被修改
    ++it;                                            //编译失败!因为const迭代器不允许被改变!
    
  • 迭代器内容常量:使用const_iterator
    std::vector<int>::const_iterator it = v.begin();  //使用了const_iterator类型
    *it = 10;                                         //编译失败,数据不允许被改变!
    ++it;                                             //编译通过,迭代器本身可以被改变
    

三、返回const

  • 尽量使用const可以帮助调试
    class Rational{....};
    Rational operator*(const Rational& lhs, const Rational& rhs){...}
    //进行如下操作
    Rational a,b,c;
    if(a*b = c){......}   
    
    注:编译器在此并不会报错,因为只有当a,b,c是C++自有类型(比如int)才会报错,对于用户自定义的类,编译器会认为此操作是将一个Rational赋值给另一个Rational
    方法:使用将该操作符定义为返回const,这样对其赋值将会是非法操作
    const Rational operator*(const Rational& lhs, const Rational& rhs){...}
    

四、成员函数与const

  • 作用:
    a、它可以让接口更加直观,直接告诉用户这个函数是不是只读(Read only),会不会改变某变量;
    b、用const修饰的对象只能调用const修饰的成员函数,因为不被const修饰的成员函数可能会修改其他成员数据,打破const关键字的限制;
    Text t("Hello");
    const Text ct("Hello");
    
    std::cout<<t[0];            //调用了不加const修饰的索引操作符
    std::cout<<ct[0];           //调用了const版本, 但如果只有不加const的操作符,将会报错discard qualifier
    t[0] = 'x';                 //成立,但注意此索引操作符必须声明为引用才可以支持赋值操作
    ct[0] = 'x';                //错误!常量不能被修改
    

五、const的数据常量性和逻辑常量性

  • 数据常量性:不允许常量对象的成员数据被修改(但只检查该成员函数有没有给成员数据进行赋值操作),但可以修改了某个数据,这样照样可以通过编译器的检测;
    const Text ct("Hello");        //构造某常量对象
    char* pc = &ct[0];             //取其指针
    *pc = 'K';                     //通过指针修改常量对象,编译不会报错,结果为"Kello"
    
  • 逻辑常量性:允许某些数据被修改,只要这些改动不会反映在外,用mutable关键字来解决;除mutable之外,静态成员(static)也可以被const成员函数修改
    mutable std::size_t length;
    mutable bool lengthValid;
    
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值