【问题标题】:the memory location of static and extern storage class in C [duplicate]C中静态和外部存储类的内存位置[重复]
【发布时间】:2016-03-17 09:38:54
【问题描述】:

我有两个共享全局变量的文件。

在 main.c 中

#include<stdio.h>
static int b;
extern int b;
main()
{
extern int a;
printf("a=%d &a:%p\n",a,&a);
printf("b=%d &b:%p\n",b,&b);
fn();
}

在 fun.c 中

#include<stdio.h>
int b=25;
int a=10;
fn()
{
printf("in fna=%d &a:%p\n",a,&a);
printf("in fnb=%d &b:%p\n",b,&b);
}

如果我编译这两个文件。我没有收到任何编译错误。它很好。输出是

a=10 &a:0x804a018 b=0 &b:0x804a024 in fna=10 &a:0x804a018 in fnb=25 &b:0x804a014

但是,在 main.c 中,如果我像这样更改 extern int bstatic int b

#include<stdio.h>
extern int b;
static int b;
main()
{
extern int a;
printf("a=%d &a:%p\n",a,&a);
printf("b=%d &b:%p\n",b,&b);
fn();
}

在编译时,我收到了这个错误。

main.c:6:12: error: static declaration of ‘b’ follows non-static declaration main.c:5:12: note: previous declaration of ‘b’ was here

这里的问题在于存储静态和外部变量的内存。但是我无法得出第二次编译错误的确切原因

注意:我使用的是 gcc 编译器。

【问题讨论】:

  • 问题是?你应该把问题分解成编译器错误的原因和编译器对特定变量的分配策略。
  • 也许你的意思是写static int a;

标签: c static compiler-errors declaration extern


【解决方案1】:

C 标准中的这两个引用(6.2.2 标识符的链接)将有助于理解问题。

4 对于使用存储类说明符 extern 声明的标识符 在该标识符的先前声明的范围内 可见,31) 如果先前的声明指定内部或外部 链接,后面声明的标识符的链接是 与先前声明中指定的链接相同。如果没有事先 声明是可见的,或者如果先前的声明指定没有 链接,则标识符有外部链接。

7 如果在一个翻译单元中,相同的标识符出现在两个 内部和外部链接,行为未定义。

在这个翻译单元中

#include<stdio.h>
static int b;
extern int b;
main()
{
extern int a;
printf("a=%d &a:%p\n",a,&a);
printf("b=%d &b:%p\n",b,&b);
fn();
}

标识符b 具有内部链接(阅读第一个引号)。 b 的第一个声明将标识符声明为由于 storage-calss 说明符 static 而具有内部链接。 b 的第二个声明与存储类说明符 extern 具有先前的声明 b(第一个声明)与存储类说明符 static。所以标识符的链接和之前声明的标识符的链接是一样的。

在这个翻译单元中

#include<stdio.h>
extern int b;
static int b;
main()
{
extern int a;
printf("a=%d &a:%p\n",a,&a);
printf("b=%d &b:%p\n",b,&b);
fn();
} 

标识符b 被声明为具有外部和内部链接(阅读两个引号)。所以编译器发出消息。

首先,标识符b 被声明为具有外部链接(因为没有事先声明具有给定链接),然后由于说明符static,相同的标识符被声明为具有内部链接。

【讨论】:

    猜你喜欢
    • 2013-12-20
    • 2023-03-07
    • 2016-06-08
    • 2015-06-13
    • 2016-02-07
    • 1970-01-01
    • 2015-02-27
    • 2011-08-16
    • 2014-05-08
    相关资源
    最近更新 更多