【发布时间】:2015-04-04 18:53:50
【问题描述】:
我正在阅读“C++ 入门加”。第9章讲了C++和C在处理const修饰符时的区别:
“在 C++(但不是 C)中,const 修饰符会稍微改变默认存储类。而全局变量默认具有外部链接,而 const 全局变量默认具有内部链接。
...
如果全局 const 声明与常规变量一样具有外部链接,这将是一个错误,因为您只能在一个文件中定义全局变量。也就是说,只有一个文件可以包含过程声明,而其他文件必须使用 extern 关键字提供引用声明。”
我尝试使用以下程序测试此声明:
文件.h:
using namespace std;
const char *constant = "Magic";
file1.cpp
#include <iostream>
#include "file.h"
extern void file2();
int main(){
cout << "constant = " << constant << endl;
file2();
}
file2.cpp
#include <iostream>
#include "file.h"
void file2(){
cout << "file2 constant = " << constant << endl;
}
生成文件:
CFLAGS = -Wall -g
INCLUDE = file.h
src = file2.cpp file1.cpp
all: $(src) $(INCLUDE)
g++ $(CFLAGS) -o file $(src)
clean:
rm -f file
当我做时,我收到以下错误消息:
g++ -Wall -g -o file file2.cpp file1.cpp
/tmp/ccdl16Tw.o:(.data+0x0): multiple definition of `constant'
/tmp/ccA3ZEHa.o:(.data+0x0): first defined here
collect2: error: ld returned 1 exit status
make: *** [all] Error 1
gcc 版本 4.8.2
更新:
如果我这样做
char* const constant = "Magic";
然后make会给我这个警告:
g++ -Wall -g -o 文件 file2.cpp 文件1.cpp
In file included from file2.cpp:2:0:
file.h:3:24: warning: deprecated conversion from string constant to ‘char*’ [-Wwrite-strings]
char* const constant = "Magic";
^
In file included from file1.cpp:2:0:
file.h:3:24: warning: deprecated conversion from string constant to ‘char*’ [-Wwrite-strings]
char* const constant = "Magic";
【问题讨论】:
-
您是否在标题中尝试了
extern const char *constant;,例如在其中一个翻译单元中尝试了const char *constant = "Magic";?在class/struct声明之外使用时,全局变量仍然不同。 -
@πάνταῥεῖ 我认为他的意思是
const应该有内部链接,所以链接器不应该抱怨重复的符号。 -
@vsoftco “我认为他的意思是
const应该有内部链接”,这显然是错误的,除非同时指定struct或classstatic在c++中有它的含义,与c不同。 -
@πάνταῥεῖ,我同意 vsoftco。这是我从书中文字的理解。顺便说一句,我忘了在我的 main() 中调用 file2,更新了。
-
@πάνταῥεῖ 不,我不认为这是错误的。
const似乎默认有内部链接(不需要static),我面前没有标准,但我用const constant = 10;尝试了OP 的程序,链接器没有抱怨重复了。这里的问题是指针不是const,正如@user2079303 回答所指出的那样