高质量C++/C编程指南-第11章-其它编程履历(1)
当前位置:以往代写 > C/C++ 教程 >高质量C++/C编程指南-第11章-其它编程履历(1)
2019-06-13

高质量C++/C编程指南-第11章-其它编程履历(1)

11.1 利用const提高函数的结实性
看到const要害字,C++措施员首先想到的大概是const常量。这可不是精采的条件反射。假如只知道用const界说常量,那么相当于把火药仅用于建造鞭炮。const更大的魅力是它可以修饰函数的参数、返回值,甚至函数的界说体。 const是constant的缩写,“恒定稳定”的意思。被const修饰的对象都受到强制掩护,可以防范意外的变换,能提高措施的结实性。所以许多C++措施设计书籍发起:“Use const whenever you need”。

11.1.1 用const修饰函数的参数

假如参数作输出用,岂论它是什么数据范例,也岂论它回收“指针通报”照旧“引用通报”,都不能加const修饰,不然该参数将失去输出成果。

const只能修饰输入参数:

u 假如输入参数回收“指针通报”,那么加const修饰可以防备意外地窜改该指针,起到掩护浸染。

譬喻StringCopy函数:

void StringCopy(char *strDestination, const char *strSource);

个中strSource是输入参数,strDestination是输出参数。给strSource加上const修饰后,假如函数体内的语句试图窜改strSource的内容,编译器将指堕落误。

u 假如输入参数回收“值通报”,由于函数将自动发生姑且变量用于复制该参数,该输入参数原来就无需掩护,所以不要加const修饰。

譬喻不要将函数void Func1(int x) 写成void Func1(const int x)。同理不要将函数void Func2(A a) 写成void Func2(const A a)。个中A为用户自界说的数据范例。

u 对付非内部数据范例的参数而言,象void Func(A a) 这样声明的函数注定效率较量底。因为函数体内将发生A范例的姑且工具用于复制参数a,而姑且工具的结构、复制、析构进程都将耗损时间。

为了提高效率,可以将函数声明改为void Func(A &a),因为“引用通报”仅借用一下参数的别名罢了,不需要发生姑且工具。可是函数void Func(A &a) 存在一个缺点:“引用通报”有大概改变参数a,这是我们不期望的。办理这个问题很容易,加const修饰即可,因此函数最终成为void Func(const A &a)。

以此类推,是否应将void Func(int x) 改写为void Func(const int &x),以便提高效率?完全没有须要,因为内部数据范例的参数不存在结构、析构的进程,而复制也很是快,“值通报”和“引用通报”的效率险些相当。

问题是如此的缱绻,我只好将“const &”修饰输入参数的用法总结一下,如表11-1-1所示。

对付非内部数据范例的输入参数,应该将“值通报”的方法改为“const引用通报”,目标是提高效率。譬喻将void Func(A a) 改为void Func(const A &a)。

对付内部数据范例的输入参数,不要将“值通报”的方法改为“const引用通报”。不然既达不到提高效率的目标,又低落了函数的可领略性。譬喻void Func(int x) 不该该改为void Func(const int &x)。

表11-1-1 “const &”修饰输入参数的法则

11.1.2 用const修饰函数的返回值

u 假如赐与“指针通报”方法的函数返回值加const修饰,那么函数返回值(即指针)的内容不能被修改,该返回值只能被赋给加const修饰的同范例指针。

譬喻函数

const char * GetString(void);

如下语句将呈现编译错误:

char *str = GetString();

正确的用法是

const char *str = GetString();

u 假如函数返回值回收“值通报方法”,由于函数会把返回值复制到外部姑且的存储单位中,加const修饰没有任何代价。

譬喻不要把函数int GetInt(void) 写成const int GetInt(void)。

同理不要把函数A GetA(void) 写成const A GetA(void),个中A为用户自界说的数据范例。

假如返回值不是内部数据范例,将函数A GetA(void) 改写为const A & GetA(void)简直能提高效率。但此时千万千万要小心,必然要搞清楚函数毕竟是想返回一个工具的“拷贝”照旧仅返回“别名”就可以了,不然措施会堕落。见6.2节“返回值的法则”。

u 函数返回值回收“引用通报”的场所并不多,这种方法一般只呈此刻类的赋值函数中,目标是为了实现链式表达。

譬喻

class A

{…

A & operate = (const A &other); // 赋值函数

};

A a, b, c; // a, b, c 为A的工具

a = b = c; // 正常的链式赋值

(a = b) = c; // 不正常的链式赋值,但正当

假如将赋值函数的返回值加const修饰,那么该返回值的内容不答允被窜改。上例中,语句 a = b = c仍然正确,可是语句 (a = b) = c 则是犯科的。

    关键字:

在线提交作业