1.基本概念
变量有数据类型: char/unsigned char/short/unsigned short/int/unsigned int long/unsigned long/ float/double
定义变量 int a = 100;//自动分配4字节的内存空间,其中存储100
2.从作用域与可见性的角度来分类
全局变量:函数之外定义的变量属于全局变量
局部变量:函数内部定义的变量属于局部变量
形参变量也是局部变量
3.特点
局部变量
1)作用域:只在其定义的函数内部有效
2)生命周期
随着函数被调用,而分配局部变量对应内存空间(生)
随着函数调用结束,局部变量对应的内存空间也收回(死)
全局变量
1)作用域
全局有效(所有函数中都可以使用)
2)生命周期
随着程序的启动,全局变量就分配了对应的内存空间(生)
随着程序的结束,全局变量对应的内存空间才回收(死)
需要注意的事项:
1)如果局部变量和全局变量重名了,函数内部会优先使用局部变量
2)局部变量的作用域与生命周期的引申
局部变量的生命始于{
结束于 }
作用域,定义该局部变量的{…}之中
3)全局变量 只定义不初始化,系统会自动将其对应的内存空间初始化为0
局部变量 只定义不初始化,其对应的内存空间中的内存不可预知
4.关键字static //静态的
可以使用它来修饰局部变量
全局变量
函数
被static修饰的全局变量,称作静态全局变量
被static修饰的局部变量,称作静态局部变量
4.1 被static修饰的局部变量
int f(void){
static int a= 0; //静态局部变量
…
}
静态局部变量,其作用域和普通的局部变量作用域相同就是函数内部 ({…}内部)
其生命周期始于程序开始运行,结束于程序结束 (全局变量的生命周期相同)
总结:static修饰局部变量 作用域不变 拉长了局部变量的生命周期
4.2 被static修饰的全局变量
mkdir static
cd static
vim main.c
#include <stdio.h>
extern int g_a;
int main(void){
g_a++;
printf("g_a=%d\n", g_a);
return 0;
}
vim func.c
#include <stdio.h>
int g_a = 100;// 全局变量
void func(void)
{
g_a++;
printf("call func \n");
}
gcc main.c func.c
./a.out //程序正常执行
修改func.c
vim func.c
int g_a = 100;// 全局变量 替换为
static int g_a = 100;
gcc main.c func.c //报错 认为找不到变量g_a
通过以上实验:
static 修饰全局变量 使得全局变量不再是全局(所有的.c)可见的
缩小为值在本文件中可见
总结:
作用域(可见性) 生命周期
局部变量 函数内部({…}内部) 随着函数调用的开始({)而开始
随着函数调用的结束(})而结束
静态局部变量 函数内部({…}内部) 随着程序的启动而开始
随着程序的结束而结束
(static拉长了局部变量的生命周期)
全局变量 全局可见(所有.c中可见) 随着程序的启动而开始
随着程序的结束而结束
静态全局变量 只在定义该变量的.c中可见 随着程序的启动而开始
其它.c文件中不可见 随着程序的结束而结束
(static缩小了全局变量的
可见性)
4.3 static修饰函数
vi main.c
extern void func(void); //func的声明
int main(){
...
func();
return 0;
}
gcc main.c func.c
./a.out
static修饰函数的作用类似于修饰全局变量
使得该函数只在定义的.c文件中见,
其它.c文件不可用
vi func.c
把 void func(void)替换为
static void func(void)
gcc main.c func.c //报错 被staic修饰的函数在其它.c文件中不可见
笔试题:谈谈对static关键字的理解?
修饰局部变量 。。。
修饰全局变量 。。。
修饰函数…
5.extern关键字
int g_a; //定义一个全局变量 意味着要分配4字节的内存空间
extern int g_a;//声明一个全局变量 告诉编译器已经存在一个变量叫g_a
//不需要编译器再去分配内存空间了
//该代码的主要目的就是告诉编译器后边再分析到g_a,
//你编译器知道它是一个int类型的变量就好了