这是三个不同的变量。他们只是碰巧有相同的名字。改变一个人的价值不会改变另一个人的价值。
变量具有关联的范围,在该范围内它是可见的。从第6.2.1节C99 标准的标识符范围:
一个标识符可以表示一个对象;一个函数;结构、联合或枚举的标签或成员;类型定义名称;标签名称;宏名;或宏参数。同一个标识符可以在程序的不同点表示不同的实体。枚举的成员称为枚举常量。宏名称和宏参数在此不再进一步考虑,因为在程序翻译的语义阶段之前,源文件中出现的任何宏名称都被构成其宏定义的预处理标记序列替换。
和:
对于标识符指定的每个不同实体,标识符仅在称为其范围的程序文本区域内可见(即,可以使用)。由同一标识符指定的不同实体要么具有不同的范围,要么位于不同的名称空间中。作用域有四种:函数、文件、块和函数原型。(函数原型是声明其参数类型的函数的声明。)
和:
每个其他标识符的范围由其声明的位置决定(在声明符或类型说明符中)。如果声明标识符的声明符或类型说明符出现在任何块或参数列表之外,则标识符具有文件范围,该范围在翻译单元的末尾终止。如果声明标识符的声明符或类型说明符出现在块内或函数定义中的参数声明列表内,则标识符具有块范围,该范围终止于关联块的末尾。如果声明标识符的声明符或类型说明符出现在函数原型(不是函数定义的一部分)的参数声明列表中,则标识符具有函数原型范围,该范围终止于函数声明符的末尾。如果标识符在同一名称空间中指定两个不同的实体,则范围可能重叠。如果是这样,一个实体的范围(内部范围)将是另一个实体范围(外部范围)的严格子集。在内部范围内,标识符指定在内部范围内声明的实体;在外部范围内声明的实体在内部范围内隐藏(不可见)。
发布代码中的每个a
(标识符)都具有函数范围,因此不会干扰a
在另一个函数中声明的内容。
静态变量将自动初始化为 0?
static
指定 的生命周期,a
即静态存储持续时间。从第6.2.4 节对象的存储持续时间:
使用外部或内部链接或存储类说明符 static声明其标识符的对象具有静态存储持续时间。对于这样的对象,保留存储空间,并且在程序启动之前,它的存储值仅初始化一次。该对象存在,具有一个常量地址,并在整个程序的执行过程中保留其最后存储的值。23)
并从第6.7.8 节初始化:
如果具有静态存储持续时间的对象未显式初始化,则:
-- 如果有指针类型,则初始化为空指针;
-- 如果它具有算术类型,则将其初始化为(正或无符号)零;
-- 如果是聚合,则每个成员都根据这些规则(递归地)初始化;
-- 如果是联合,则根据这些规则(递归地)初始化第一个命名成员。
所以a
被初始化为0
。