呐呐呐 讲不清const的细节你就不用来上班啦

287 阅读4分钟

本文是小生学习道路上的见解,尽最大可能保证正确性,如有不当还请大佬执教。

       当小生逐渐从当初的愣头青成长到现在的进阶版愣头青,简历也逐渐花了起来。刚开始还会被问到一些基础问题,现在面试官基本上来就是多态起步,导致自己也渐渐对这些语法的细节生疏了起来。用还是会用的,但就是被问到的话就阿巴阿巴憋不出让人满意的回答……所以就跟着我一起复习一下叭~

const的定义

在《C++ Primer(5th edition)》中,const被称为限定符,最本质的意义就是“定义一个值不能改变的变量”。

我:“面试官我说完了。”
面试官:“?”

最基本的使用中,假如我们希望定义一个大小固定的缓冲区,此时就会用到const来修饰:

const int bufferSize = 1024;    //用const对int型变量bufferSize进行限定
bufferSize = 512;    //报错:你tm敢动const?

请注意,由于const不可被改变的特性,在定义const变量时必须初始化,否则在赋值时将调用赋值运算符operator=,与const的定义相违背。

const int i;    //报错:爷的初始化呢?
const int i = 1;
int j = 2;
const int k = j;    //正确,使用拷贝构造函数初始化

const修饰不同对象的表现

  1. 修饰基本类型

      这一点在定义部分已经用int举过例子了,其他的聪明的你一定懂得叭?

  2. 修饰复合类型

      复合类型包括引用和指针。
在引用的的定义中,引用的类型必须与其所引用的对象的类型一致。那么对应到带有const限定符修饰的对象,它的引用应该长这个样子:

const int i = 1;
const int &j = i;    //非常地合理
j = 2;    //报错:试图修改常量
int &k = i;    //报错:引用类型与对象类型不一致

       但是,引用,是存在特例的!是的没错!在上面的例子中,你应该已经注意到了,我并没有列举引用类型使用了const修饰,而对象类型并没有的情况,像这样:

int i = 1;
const int &j = i;    //会报错吗??

       实际上并不会报错,并且还包含更离谱的情况:

int i = 1;
const int &j = i * 2;    //这等号左边已经是右值了啊!!
double a = 1.0;
const int &b = a;    //不只是const没对上,连对象类型都变了啊喂!

       翻阅《C++ Primer(5th edition)》,会知道这其中发生了隐式转换。至于为什么C++允许这样的语法出现,小生觉得只能靠理解记忆了。毕竟用一个const引用去引用一个非const对象,只是多加了一个不能修改该对象的限定,也是合情合理的叭……

我是一名汽车维修员,所以随身带着扳手也是合情合理的。

       有了引用的基础,指针就简单多了,通过一波任意组合,就能够得到const和指针的不同搭配用法了:

const int *i;    //指向const int的指针
int const *i;    //与上面一致
int *const i;    //const指针,指向int型对象

       我们说过(其实没有),从汇编层面上看,引用和指针的实现原理是完全一致的,所以引用中的所有情况都能在指针中找到对应的用法:

int i = 1;
const int *j = &i;    //合理
const int i = 1;
int *j = &i;    //你小子试图突破我const的防御??

       带有隐式转换的也一样:

double i = 1.0;
const int *j = &i;

        对于这种指针为常量或者指针指向的对象为常量的情况,为了便于称呼,C++中给它们分别取了个名字。指针为常量的称为顶层const(top-level const),另一种情况叫底层const(low -level const)。后面讲重载的时候会用到。

    3. 修饰函数

const int fun(int x);    //修饰返回值
int fun(const int x);    //修饰参数
int fun(int x)const;    //修饰函数

重点在于修饰函数的情况。作为成员函数时,常函数不允许修改成员变量,不允许调用非const函数。

   4. 修饰对象

       const对象只允许调用const成员函数。

进阶:我为什么建议你使用const

回想起大一时,老师说:“一个优秀的程序员,代码里一定会经常出现const。”。

       在阅读《Effective C++》时,我悟到了大佬对于const的见解:假如你是一个优秀的程序员,你同事也是,那不加const或许没事。但如果这两个条件其中一个为false,那就该const就const!

高阶:使用了const后,一切真的如我们所愿吗?

       我们都知道,如果声明了一个函数为const,但又希望它能够更改某些成员变量,那我们会使用mutable关键字来修饰变量,表示它不受const的限制。

       但,一定要有mutable,const函数才能对成员变量做出修改吗?

2020.4.11 未完待续嘻嘻,复习时间8多,小生尽量在面面俱到后再深入每一个知识点。