声明
声明可声明多次,而编译器不会为其分配存储空间。目的是为了使编译器知道该标识符所代表的含义及原型所在,文件与文件之间 使用关键字 extern 修饰变量或函数称为声明(引用)可使同工程目录下的变量或函数实现交互 说明符 + 表达式列表
定义
一般的情况下,把建立空间的声明称之为定义,而把不需要建立存储空间的声明称之为声明。
int a = 1; // 定义
int main() {
int b; // 也是定义,因为建立了存储空间
extern int a; // 声明定义在别处的变量,仅仅是声明,没有建立空间
}
a 被声明了两次,第一次声明为变量预留了存储空间构成了定义。称为定义式声明。第二次声明只是使用之前的变量,而没有创建空间所以仅仅是声明。
extern关键字只能做声明,不能定义。有extern关键字都是声明,其它情况都是变量的定义。
初始化
变量的初始化: 为变量声明或者定义之后,赋上初值的过程,就是变量的初始化。
定义、声明、初始化的区别
// 对于全局变量
extern int a; // 仅仅是声明
int a = 4; // 定义 + 初始化
int a; // 可能是定义也可能是声明,因为该全局变量未初始化,如果其他文件中定义了该变量,则该变量为弱符号,则为声明,否则为强符号,为定义。
// 对于局部变量
int a; // 一定是定义,因为这时已分配内存空间
a = 4; // 赋值
下面这个叫做赋值,因为在定义变量时,并没有赋值
int b; // 声明/定义 变量
b = 2; // 初始化变量
静态变量初始化
静态变量(被static关键字修饰过的变量)默认将值初始化为0。可执行程序载入到内存时,已经保存了正确值的位置,会将值赋值给变量。完成这个任务不需要额外的时间与指令,静态变量就会初始化完成。
自动变量初始化
自动变量(可以简单理解为局部变量)不会被初始化为0。程序在链接时还无法判断自动变量的存储位置,因为局部变量可能在函数中每次调用时占据不同位置。所以自动变量会使用更多开销。
- 自动变量的初始化和声明然后赋值,效率一样,无差别。
- 静态变量每次只在程序执行时初始化一次,而自动变量在每次执行到所在函数时都会进行一次初始化。
- 因为自动变量初始化在运行时才执行,你可以用变量给他初始化, 而静态变量不能使用变量来初始化 。
int a = 4;
int b = a + 3;
// static int c = a + 4; 编译报错
-
建议对自动变量初始化,或者保证使用前赋值,不然它会有一个垃圾值是非预期的,会导致程序出现意料之外的bug。
垃圾值演示
#include<iostream>
using namespace std;
struct T {
int a;float b;string c;int d[100];int *e;
friend ostream &operator<<(ostream &os, const T &t) {
os << "a: " << t.a << " b: " << t.b << " c: " << t.c << " d: " << t.d << " e: " << t.e;
return os;
}};
int main(int argc, char const *argv[]) {
// 产生垃圾值
int a;
float b;
string c;
int d[100];
int *e;
T f;
e = &a;
//// 初始化后不会产生垃圾值
// int a = 0;
// float b = 0;
// string c{};
// int d[100] = {};
// int *e;
// T f{};
// e = &a;
cout << a << endl;
cout << b << endl;
cout << c << endl;
cout << d << endl;
cout << e << endl;
cout << &a << endl;
cout << f << endl;
for (const auto &item: d){
std::cout << item << std::endl;
}
return 0;
}
标签:初始化,定义,int,C++,extern,声明,变量
From: https://www.cnblogs.com/hhddd-1024/p/17760789.html