2

据我所知,一个全局变量在 C 中可能是一到两个不同的存储类,并且声明可以用两个不同的关键字给出,相应地

extern int foo; //default
static int bar;

静态变量只在声明模块内可见,不能导出。在外部声明的情况下,该变量位于所有链接模块的公共命名空间中,除非被静态变量遮蔽。

静态变量必须在其模块中定义,而外部变量可以在其他地方定义。如果曾经使用过,则必须对其进行定义。

我的编译器(GCC)接受

static int bar = 5;

但抱怨

extern int foo = 4;

似乎期望外部变量永远不会用关键字“extern”定义。这导致了以下问题

上例中的 Object 'foo' 在定义它的模块中有什么样的存储类?

4

4 回答 4

2

IIRC,extern更像是对编译器的提示,它不必为该值分配存储空间。链接器应在另一个编译单元中找到该值。通常extern用在头文件中,表示某人已定义与名称关联的存储。该值的定义不包括extern关键字,因为编译器必须为包含该定义的编译单元中的值分配存储空间。

有关更多详细信息,请参阅外部存储类说明符

于 2011-04-12T11:45:01.203 回答
0

实际上,您错过了两个存储类:auto 和 register
Register 在这里无关紧要,但默认存储类是 auto。
自动为内存中某处的变量保留空间(这通常是您声明变量时想要的)。应该注意的是,每次进入变量范围时,都会为“自动变量”分配新空间。(即,当 func() 声明一个“auto”变量时,从 func() 中调用函数 func() 将产生两个不同的变量,并且每次调用 func() 只会知道它自己的变量。
由此得出 auto 变量在全局范围内声明将是唯一的(因为该范围仅输入一次)。
然而,静态变量总是唯一的。独特的空间只会被分配一次。当 func() 调用 func() 并且您希望两个函数调用对同一个变量进行操作时,这很有用。
外部变量只是对唯一变量的引用。
当您想要访问在不同文件中声明的全局变量时,您可以使用它们。
鉴于文件 1.c 和 2.c,声明“int global;”是不够的。在这两个文件中,因为空间将被分配两次,并且名称冲突会导致链接错误。
因此,您所做的是在一个文件中保留空间(使用“int global;”),并在另一个文件中告诉链接器通过编写“extern int global;”在另一个文件中查找名称为“global”的变量。

于 2011-04-12T12:03:56.960 回答
0

extern 变量将在定义它的单元中使用全局范围(导出)进行定义:

int baz = 5;

于 2011-04-12T11:41:47.010 回答
0

默认存储类是auto.

于 2011-04-12T11:42:34.533 回答