2013-08-25 100 views
3

我有一個.h文件,我打算只用於存儲將顯示在我的程序中的所有信息字符串。在我info.h:C鏈接錯誤多重定義

#ifndef __INFO_H 
#define __INFO_H 

char *info_msg = "This is version 1.0 of NMS."; 

//all other strings used by view.c and controller.c 

#endif 

然後在我的view.h我有如下:

我或者Controller.h使用view.h:

//controller.h 
#ifndef __CONTROLLER_H 
#define __CONTROLLER_H 

#include "view.h" 
#include "model.h" 
//other stuff line method declaration etc. 
#endif 

爲主。 c:

#include "controller.h" 
int main() 
{ 
    //stuff 
} 

view.c:

#include "view.h" 

char esc,up,down,right,left; 
void change_character_setting(char pesc, char pup, char pdown, char pright, char pleft) 
{  
    esc = pesc; 
    up = pup; 
    down = pdown; 
    right = pright; 
    left = pleft; 
} 


void print_warning() 
{ 
printf("%s \n",info_msg); 
} 

當我試圖創建鏈接抱怨可執行文件:

/tmp/ccqylylw.o:(.data+0x0): multiple definition of `info_msg' 
/tmp/cc6lIYhS.o:(.data+0x0): first defined here 

我不知道爲什麼會看到兩個定義,因爲我使用的是保護塊。我試圖谷歌在這裏,但沒有具體顯示。有人可以解釋它是如何看到多個定義的?我如何在Java中實現簡單的操作,以便在C中使用單個文件進行所有文本操作?

+0

切勿在頭文件中分配變量。在頭文件中聲明它們爲extern,並在源文件中定義它們。編譯器爲每個包含創建一個實例(例如,在每個編譯單元/源文件中)。這會在鏈接時創建錯誤。 – bash0r

+0

謝謝。現在我收到以下錯誤:/tmp/ccFMbvlv.o:在函數'print_warning'中: view.c :(.text + 0x44b):未定義的引用'info_msg' – as3rdaccount

+0

您可以編輯您的答案併發布view.c ? – bash0r

回答

4

您正在編譯一個名爲info_msg的全局變量到每個包含info.h的源文件中,這些文件可以是直接的,也可以是從其他標題中拉入的。在鏈接時,鏈接器會查找所有這些info_msg標識符(編譯的每個目標文件中都有一個),並且不知道要使用哪一個。

更改你標題是:

#ifndef PROJ_INFO_H 
#define PROJ_INFO_H 

extern const char *info_msg; // defined in info.cpp 

#endif 

並假設你有一個info.cpp(如果不是你可以把這個在任何.cpp文件,而是一個將是最自然的位置,以保持它):

// info.cpp 
#include "info.h" 

const char *info_msg = "This is version 1.0 of NMS."; 

注意:在爲下劃線的位置聲明預處理器符號和標識符時要小心。根據C99標準:

C99 §7.1.3/1

  • All identifiers that begin with an underscore and either an uppercase letter or another underscore are always reserved for any use.
  • All identifiers that begin with an underscore are always reserved for use as identifiers with file scope in both the ordinary and tag name spaces.
+2

保留包含*'__'的任何內容。 – chris

+0

@chris whoa。請參考。 (我不懷疑你,我只是想讀它)。謝謝。 – WhozCraig

+0

[保留標識符](http://stackoverflow.com/questions/228783/what-are-the-rules-about-using-an-underscore-in-a-c- identifier) – chris