1.作用域(决定变量在哪里可见,哪里销毁)
代码块作用域:隶属于函数的,包括函数的形参,函数结束就销毁
函数原型作用域:函数原型的名字无关紧要,除了变长数组中的声明。
文件作用域:函数外面定义的变量,整个文件都是可见的。
2.链接
空链接:代码作用域和函数原型作用域都是空链接,私有的。
外部链接:多文件任何地方可用。
内部链接:单文件可用,使用static定义的。
3.存储时期
静态存储时期:程序运行时一直存在,文件作用域变量属于这种
自动存储时期:代码块进入时定义,退出时释放,代码块作用域变量属于这种
4.自动变量
内层代码块定义了和外层代码块同一名字的变量,会发生覆盖
自动变量不会被自动初始化
- #include<stdio.h>
- int main(void){
- int x = 30;
- printf("x in outer block:%d\n",x);
- {
- int x = 77;
- printf("x in inner block:%d\n",x);
- }
- printf("x in outer block:%d\n",x);
- while(x++<33){//此处并没有声明一个x,所以继续使用外部定义的x
- int x = 100;//发生了覆盖
- x++;
- printf("x in while block:%d\n",x);
- }
- printf("x in outer block:%d\n",x);
- getchar();
- return 0;
- }
5.寄存器变量
无法获得寄存器的地址
仅仅是一个请求,不确保一定能使用寄存器
即使请求失败,仍然不能使用取地址符号&
可以处理的数据类型有限,例如double可能就无法处理
6.代码块静态变量
必须使用static在代码块内创建
可以自动初始化为0
静态变量和外部变量在程序调入内存时已经存在了。
- #include<stdio.h>
- void trystat(void);
- int main(void){
- int count;
- for(count=1;count<=3;count++){
- printf("Here comes iteration %d:\n",count);
- trystat();
- }
- getchar();
- return 0;
- }
- void trystat(void){
- int fade = 1;//每次调用函数时,fade都被初始化
- static int stay = 1;//只在编译函数时被初始化一次,它不是运行时执行的语句。
- printf("fade = %d and stay = %d\n",fade++,stay++);
- }
7.外部链接的静态变量(全局变量)
使用extern关键字来声明变量,说明变量在其他地方定义。
当我们在函数中使用外部链接的静态变量时,,不需要声明就可以直接使用,如果显式的声明,必须加extern关键字,否则会声明一个内部变量覆盖全局的静态变量。
自动初始化为0,不能用变量初始化
不能用extern来进行外部定义,只用它来引用一个已经存在的外部定义
- int Hocus;//全局
- int magic();
- int main(void){
- int Hocus;//局部
- ...
- }
- int pocus;//只对 magic可见而对main不可见
- int magic(){
- auto int Hocus;//局部
- }
8.内部链接的静态变量
使用static进行定义,只能在单一文件中使用。