我有一个头文件和两个源文件。在所述头文件中,我有以下声明:包含数组声明头时出错
const char *letters[] = {"A", "B", "C", "D"};
我在两个源文件中都包含了我的头文件。当我尝试编译,我得到:
/tmp/cc6gLw9s.o:(.data+0xa0): multiple definition of `letters'
/tmp/ccjqd0rr.o:(.data+0xa0): first defined here
我有一个头文件和两个源文件。在所述头文件中,我有以下声明:包含数组声明头时出错
const char *letters[] = {"A", "B", "C", "D"};
我在两个源文件中都包含了我的头文件。当我尝试编译,我得到:
/tmp/cc6gLw9s.o:(.data+0xa0): multiple definition of `letters'
/tmp/ccjqd0rr.o:(.data+0xa0): first defined here
如果单独编译2的源文件和他们每个人包括头,那么变量letters
将被宣布两次,一次在每一个源文件。为了防止这种情况,在头文件中声明变量为extern
。
extern const char *letters[];
然后,把实际的变量在源文件。
const char *letters[] = {...};
关于全局变量,尤其是那些与外部链接有关的全局变量,为什么会有问题,您能否加上一两句话?这是唯一让我困扰的答案。 – StoryTeller
我不太确定该说些什么。我知道他们很丑陋,但我从来没有真正有过任何经验,因为他们过去特别麻烦,因为我主要使用团结建设。 – bace1000
这与构建封装的好设计没有多大关系。它也成为多线程程序中的噩梦。但好吧,NVM。 – StoryTeller
在C中包含文件几乎是从字面上复制和粘贴它。如果在同一个编译中包含两次头文件,就好像该代码被写入了两次。
这通常通过使用预处理器来避免标头被编译两次而避免。
#ifndef _MYHEADERS_H_
#define _MYHEADERS_H_
const char *letters[] = {"A", "B", "C", "D"};
#endif
这是除了在其他答案中提出的问题。
除了@Schwern's answer,你也可以这样做:
#pragma once
const char *letters[] = {"A", "B", "C", "D"};
注意#pragma once
不是标准C,但它是supported on most compilers。
您有多次定义的相同变量,它是一个数组,但仍然是一个变量。你不应该把变量**定义**放在头文件中。 – StoryTeller
这在技术上不是*编译器*错误,而是*链接器*错误,并且意味着您*定义了多个[*翻译单元*]中的变量(https://en.wikipedia.org/wiki/Translation_unit_%28programming %29)(基本上所有包含头文件的源文件)。不要*在头文件中定义变量(或函数)。 –