Effective C++ 学习笔记 条款03 尽可能使用const
只要某值会保持不变,就应该说出来,即定义为const的。
const int *pi = nullptr;
int const *pi = nullptr; // 两者等价
STL的迭代器就像T*指针,将迭代器声明为const的表示一个const指针,即T *const。如果想表示迭代器指向的东西不可被改动,应使用const_iterator。
const返回值用于有理数乘法:
class Rational { /* ... */ };
const Rational operator*(const Rational &, const Rational &);
返回值是const的从而避免:
Rational a ,b, c;
(a * b) = c; // 如果a*b结果不是const的,那么它不会报错
const的局部成员可以避免在条件判断时将==写为=。
const成员函数标识了哪些函数可以改动对象内容。如果两个成员函数只是const差异,那么它们是一对重载函数。
const成员函数如下标运算符,返回结果应该是const元素的引用,而非const成员函数的返回结果是元素的引用。
一个const的成员函数不能改变成员,除非成员是mutable的,但const成员函数可以改变成员指针所指的值。
当两个成员函数除了const之外都一样时,可以使用const成员函数完成其non-const孪生兄弟函数:
class TextBlock {
public:
const char &operator[](std::size_t position) const {
return text[position];
}
char &operator[](std::size_t position) {
return const_cast<char &>(static_cast<const TextBlock &>(*this)[position]); // 书上版本
return const_cast<char&>((*this)[position]); // 错误,因为*this是一个TextBlock类型对象,它会调用非const的成员函数,从而无限递归自己
}
};
以上,我们使用了static_cast为TextBlock添加const属性,使其调用const的下标运算符。而使用const_cast移除返回的char引用的const属性。const对象优先使用const版本成员函数,非const对象优先使用非const版本成员函数,而const对象不能使用非const版本成员函数,但非const对象能使用const版本成员函数。
但在const版本中使用非const版本函数完成工作是不应该的,因为const版本作出了不改变其对象状态的承诺。