第3课 - 进化后的const分析
第3课 - 进化后的const分析
1. C 语言中的 const
(1)const 修饰的变量具有只读属性,本质还是变量,只是告诉编译器该变量不能出现在赋值符号的左边。
(2)const 修饰的局部变量在栈上分配空间,修饰的全局变量在只读存储区分配空间。
(3)const 只在编译期间有用,在运行期间无用。const 不能定义真正意义上的常量(const英文含义)!
(4)C 语言中的常量只有枚举这一种类型。
1 #include <stdio.h> 2 3 int main(void) 4 { 5 const int i = 10; 6 7 int *p = (int *)(&i); // 取得 i 变量的地址 8 9 *p = 1; 10 11 printf("i = %d\n", i); // i = 1 12 13 14 return 0; 15 }
1 #include <stdio.h> 2 3 const int i = 10; 4 5 int main(void) 6 { 7 int *p = (int *)(&i); 8 9 *p = 1; // 发生段错误 10 11 printf("i = %d\n", i); 12 13 return 0; 14 } 15 16 /*** 17 程序会发生段错误,const修饰的全局变量放在只读存储区,不能通过指针进行修改 18 ***/
2. C++ 中的 const
C++ 在 C 的基础上对 const 进行了进化处理。
(1)当编译器碰见 const 声明时在符号表中放入常量。
(2)编译过程中若发现使用常量则直接以符号表中的值替换。
何为符号表?符号表是编译器在编译程序时产生的一张表格,其本质是编译器在编译程序时产生的一种数据结构。
(3)编译过程中若发现下述情况则给对应的常量分配存储空间。
① 对 const 常量使用了 extern 关键字
② 对 const 常量使用 & 操作符
Note1:C++ 编译器虽然可能为 const 常量分配内存空间,但不会使用其存储空间中的值,这样做只是为了兼容 C 语言。
Note2:何为兼容? C++ 完全兼容 C 指的是,用C编译器能编译通过的 C 程序,使用 C++ 编译器也可以成功编译,但是执行结果不一定相同。
1 #include <stdio.h> 2 3 int main() 4 { 5 const int c = 0; //C语言中会为变量c分配内存 6 int* p = (int *)&c; //C++中遇到&才为c分配内存 7 8 printf("Begin...\n"); 9 10 *p = 5; 11 12 printf("c = %d\n", c); // C语言会输出内存中的5 13 // C++中会从符号表(而不是内存)中取值,所以为0 14 15 printf("*p = %d\n", *p); 16 17 printf("End...\n"); 18 19 return 0; 20 } 21 22 // 在C中的输出结果: c = 5 , *p = 5 23 // 在C++中的输出结果:c = 0 , *p = 5
3. 对比 C/C++ 中的 const
本质 | 分配内存 | |
C | 只读变量 |
局部变量分配在栈上;全局变量分配在只读存储区 |
C++ | 常量 |
当使用 & 操作符对 const 常量取地址时会分配内存空间; 当 const 修饰全局变量,并且在其它文件中使用 extern 引用时会分配内存空间 |
4. C++ 中的 const 与宏的区别
定义 | 处理方式 | |
C++ 中的 const | const int c = 5; | 由编译器处理,编译器会进行类型检查和作用域检查 |
宏 | # define c 5 | 由预处理器处理,只是简单的文本替换 |
1 #include <stdio.h> 2 3 void f() 4 { 5 #define a 3 // 宏没有作用域的概念 6 const int b = 4; // const有作用域的概念,只在f()内部有效,g()不能引用 7 } 8 9 void g() 10 { 11 printf("a = %d\n", a); 12 printf("b = %d\n", b); // 这里会发生错误 13 } 14 15 int main() 16 { 17 const int A = 1; 18 const int B = 2; 19 int array[A + B] = {0}; // 在C中编译该句代码时,由于 A+B 两个变量的和只能在运行时确定,因此会报错 20 // C++可以从符号表中取得A + B的值为3 21 int i = 0; 22 23 for(i=0; i<(A + B); i++) 24 { 25 printf("array[%d] = %d\n", i, array[i]); 26 } 27 28 f(); 29 g(); 30 31 return 0; 32 }
5. 小结
(1)与 C 语言不同,C++ 中的 const 不是只读变量
(2)C++ 中的const是一个真正意义上的常量
(3)C++ 编译器可能会为 const 常量分配空间
(4)C++ 完全兼容 C 语言中的 const 常量的语法特性
注:本文总结于狄泰唐老师的《C++深度解析》课程
狄泰QQ群:199546072
本人QQ号:502218614