7.h:
int a
5.C:
#include"7.h"
#include <stdio.h>
int b;
void way();
void way() {
printf("%p\n",&b);
}
6.C:
#include "7.h"
#include <stdio.h>
void way();
int b;
int main(int argc, char const *argv[])
{
way();
printf("%p\n",&b);
return 0;
}
为什么我可以使用“gcc -std = c90 5.c 6.c”来成功编译它!
结果是 0x10288b018 0x10288b018
相同的地址!!!!!!但我不使用extern!为什么!
但我将“6.c”更改为:
6.C:
#include "7.h"
#include <stdio.h>
void way();
int b=8;
int main(int argc, char const *argv[])
{
way();
printf("%p\n",&a);
return 0;
}
5.c to:
#include"7.h"
#include <stdio.h>
int b=5;
void way();
void way() {
printf("%p\n",&a);
}
但结果是:
duplicate symbol _b in:
/var/folders/sb/dc6wxwf16kl7k1wrhrxjx5j40000gn/T/5-00d5c1.o
/var/folders/sb/dc6wxwf16kl7k1wrhrxjx5j40000gn/T/6-2b050b.o
ld: 1 duplicate symbol for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
答案 0 :(得分:2)
extern
关键字不是必需的。根据C99标准:
6.7.5.3.17:如果声明发生在任何函数之外,则标识符具有文件范围和外部链接。
您的两个示例之间的区别在第6.9.2.4节中解释:
int i1 = 1; // definition, external linkage int i4; // tentative definition, external linkage
标准规定i1
是定义,而i4
是暂定定义。有多个定义是一个错误;有多个暂定的定义不是。
如果某个实体具有非暂定定义,则所有暂定定义均指它;否则,多个暂定定义指的是同一个实体。