目录
const的基本理解
C和C++中const的区别
代码段
不初始化or初始化
常变量or常量
编译方式
备注开发环境:vscode通过ssh连接虚拟机中的ubuntu,ubuntu-20.04.3-desktop-amd64.iso
const的基本理解
const修饰的变量不能作为左值
const修饰的变量初始化完成后,值不能被修改
C和C++中const的区别
在C中,可以不初始化const修饰的量;在C++中,必须初始化const修饰的量
C和C++对于const的编译方式不同
在C中,将const修饰的量当作变量来编译,const修饰的量称为常变量
在C++中,const修饰的量有如下两种情况:
1、const修饰的量被初始化成一个立即数,称为常量
对于这种情况,在编译时,const常量的名字都被替换成常量的初始化值
2、const修饰的量被初始化成一个变量,称为常变量
代码段
不初始化or初始化
// 文件命名为const.c
// 使用gcc const.c -o const_c可以通过编译
// 以下代码用于演示在C中可以不初始化const修饰的量
#include<stdio.h>
void main()
{
const int a;
// 在C中可以不初始化const修饰的量
}
// 文件命名为const.cpp
// 使用g++ const.cpp -o const_cpp未能通过编译
// 以下代码用于演示在C++中必须初始化const修饰的量
#include<iostream>
int main()
{
const int a;
// 在C++中必须初始化const修饰的量
// 此处未初始化,导致未能通过编译
return 0;
}
/*
const.cpp: In function ‘int main()’:
const.cpp:9:15: error: uninitialized const ‘a’ [-fpermissive]
9 | const int a;
| ^
*/
常变量or常量
// 文件命名为const.c
// 使用gcc const.c -o const_c未能通过编译
#include<stdio.h>
void main()
{
const int a = 20;
int A[a] = { };
// 此处是错误的用法
// 在C中,将const修饰的量当作变量来编译,const修饰的量称为常变量
// C语言标准要求数组的大小必须是一个常量表达式,数组的大小必须在编译时就能确定
// a虽然被声明为const int类型,但是它在运行时才被初始化为20
// 因此,a不是一个常量表达式,而是一个常变量,不能用作数组的大小
}
/*
const.c: In function ‘main’:
const.c:10:5: error: variable-sized object may not be initialized
10 | int A[a] = { };
| ^~~
*/
// 文件命名为const.cpp
// 使用g++ const.cpp -o const_cpp可以通过编译
#include<iostream>
int main()
{
const int a = 20;
int A[a] = { };
// 此处是正确的用法
// 在C++中,const修饰的量被初始化成一个立即数,称为常量
// 对于这种情况,在编译时,const常量的名字都被替换成常量的初始化值
// 所以数组的大小在编译时就能确定
return 0;
}
// 文件命名为const.cpp
// 使用g++ const.cpp -o const_cpp可以通过编译
#include<iostream>
int main()
{
int b = 20;
const int a = b;
int A[a] = { };
// 此处是不规范的用法,不建议这样使用
// 在C++中,const修饰的量被初始化成一个变量,称为常变量
// 这种情况与“在C中,将const修饰的量当作变量来编译,const修饰的量称为常变量”类似
// C++标准中,并没有直接支持在数组大小中使用运行时的非常量表达式
// 根据C++标准,在定义数组时,数组的大小必须是一个常量表达式,即在编译时就能确定的值
// 那为什么可以通过编译呢?比较合理的解释应该是:
// 编译器对变长数组提供了一种扩展特性,允许变长数组的大小在运行时确定
// 需要注意的是,变长数组只在支持该特性的编译器中可用
// 变长数组(Variable Length Array,VLA)
return 0;
}
编译方式
// 文件命名为const.c
#include<stdio.h>
void main()
{
const int a = 2;
int * p = (int *)&a;
*p = 99;
// a由const修饰,a不能作为左值
// a的内存中的值仍然可以被修改
printf("%d %d %d\n", a, *p, *(&a));
// 在C中,将const修饰的量当作变量来编译
// 最终输出结果为99 99 99
}
// 文件命名为const.cpp
#include<iostream>
int main()
{
const int a = 2;
int * p = (int *)&a;
*p = 99;
// a由const修饰,a不能作为左值
// a的内存中的值仍然可以被修改
printf("%d %d %d\n", a, *p, *(&a));
// 在C++中,const修饰的量被初始化成一个立即数,称为常量
// 对于这种情况,在编译时,const常量的名字都被替换成常量的初始化值
// 最终输出的结果会因编译器和操作系统的不同而有所差异
// Windows 10下,在Dev C++中选用TDM-GCC 4.9.2 64-bit Debug,输出2 99 2
// ubuntu-20.04.3-desktop-amd64.iso下,输出2 99 99
return 0;
}