2.4 const限定符
下列for循环语句有两个问题,两个都和使用512作为循环上界有关。
for (int index = 0; index != 512; ++index) { // ... } |
第一个问题是程序的可读性。比较index与512有什么意思呢?循环在做什么呢?也就是说512作用何在?[本例中,512被称为魔数(magic number),它的意义在上下文中没有体现出来。好像这个数是魔术般地从空中出现。]
第二个问题是程序的可维护性。假设这个程序非常庞大,512出现了100次。进一步假设在这100次中,有80次是表示某一特殊缓冲区的大小,剩余20次用于其他目的。现在我们需要把缓冲区的大小增大到1024。要实现这一改变,必须检察每个512出现的位置。我们必须确定——在每种情况下都准确地确定——哪些512表示缓冲区大小,而哪些不是。改错一个都会使程序崩溃,又得回过头来重新检查。
解决这两个问题的方法是使用一个初始化为512的对象:
int bufSize = 512; // input buffer size for (int index = 0; index != bufSize; ++index) { // ... } |
通过使用好记的名字如bufSize,增强了程序的可读性。现在是对对象bufSize测试而不是对字面值常量512测试:
现在如果想要改变缓冲区大小,就不再需要查找和改正80次出现的地方。而,只有初始化bufSize那行需要修改。这种方法不但明显减少了工作量,而且还大大减少了出错的可能性。
1. 定义const对象
定义一个变量代表某一常数的方法仍然有一个严重的问题。即bufSize是可以被修改的。bufSize可能被有意或无意地修改。const限定符提供了一个解决办法:它把一个对象转换成一个常量。
const int bufSize = 512; // input buffer size |
定义bufSize为常量并初始化为512。变量bufSize仍然是一个左值(2.3.1节),但是现在这个左值是不可修改的。任何修改bufSize的尝试都会导致编译错误:
bufSize = 0; // error: attempt to write to const object |
因为常量在定义后就不能被修改,所以定义时必须初始化:
const std::string hi = "hello!"; // ok: initialized const int i, j = 0; // error: i is uninitialized const |
2. const对象默认为文件的局部变量
在全局作用域(2.3.6节)里定义非const变量时,它在整个程序中都可以访问。我们可以把一个非const变量定义在一个文件,假设已经做了合适的声明,就可在另外的文件中使用这个变量:
// file_1.cc int counter; // definition // file_2.cc extern int counter; // uses counter from file_1 ++counter; // increments counter defined in file_1
|
与其他变量不同,除非特别说明,在全局作用域声明的const变量是定义该对象的文件的局部变量。此变量只存在于那个文件,不能被其他文件访问。
通过指定const变量为extern,就可以在整个程序中访问const对象:
// file_1.cc // defines and initializes a const that is accessible to other files extern const int bufSize = fcn(); // file_2.cc extern const int bufSize; // uses bufSize from file_1 // uses bufSize defined in file_1 for (int index = 0; index != bufSize; ++index) // ... |
本程序中,file_1.cc通过函数fcn()的返回值来定义和初始化bufSize。而bufSize定义为extern,也就意味着bufSize可以在其他的文件中使用。file_2.cc中bufSize的声明同样是extern,这种情况下,extern标志着bufSize是一个声明,所以没有初始化式。
非const变量默认为extern。要使const变量能够在其他的文件中访问,必须显式地指定它为extern。
习题
习题2.22 下列程序段虽然合法,但是风格很糟糕。有什么问题呢?又怎样改善?
for (int i = 0; i < 100; ++i) // process i
|
习题2.23 下列哪些语句合法?对于那些不合法的使用,解释原因。
(a) const int buf; (b) int cnt = 0; const int sz = cnt; (c) cnt++; sz++;
|
【责任编辑:
董书 TEL:(010)68476606】