簡體   English   中英

將 extern 用於全局變量的正確方法是什么?

[英]What is the correct way of using extern for global variables?

文件 a.cc

int a = 0;

文件 b.cc

#include "a.cc"

文件 main.cc

#include "b.cc"
extern int a;

int main() {


}

g++ -c a.cc
g++ -c b.cc
g++ main.cc a.o b.o
error: multiple definitions of a

我在這里做錯了什么?

您包含.cc (或.cpp )文件,這是錯誤的。 不要那樣做。 你需要一個 header,然后把extern int a;

// a.h
// include guards omitted
extern int a;

// a.cc
#include "a.h"

int a;

// b.cc
#include "a.h"

// main.cc
#include "a.h"

int main(){
  // use a
}

您所做的正是 linker 所說的:您提供了“a”的多個定義。 a.cc 和 b.cc 都將變量 'a' 定義為具有外部鏈接的東西。

不要那樣做!

不要#include 源文件。 有時您確實想這樣做,但話又說回來,有時您想使用goto

正是編譯器告訴你的——你最終在所有三個翻譯單元中定義a :你希望它反過來:重復包含的聲明應該是 extern,並且必須只有一個定義。 例如:

// header: stuff.h
extern int a;
void foo();


// first TU: a.cpp
#include "stuff.h"

void foo() { a += 1; }


// second TU: main.cpp
#include "stuff.h"

int a; // `a` is stored in this TU

int main() {
  a = 6;
  foo();
  //  now a == 7
}

使用包含時,想象將所有文件放在一個文件中。 這基本上就是編譯器所看到的,因為在編譯器階段之前,預處理器已經包含了所有內容。

所以你的 main.cc 開始看起來像這樣。

int a;
extern int a;

編譯器認為這沒問題,因為沒有初始化程序的 extern 只是一個聲明,因此沒有為它分配 memory。 然而,“int a”是一個定義,因此 main.o 包含為 a 分配 memory 的指令。

鏈接后,linker 會注意到 ao 和 bo 也已經定義了“a”。 “a”是因為這是它最初定義的地方,而“b”是因為 b 包括具有定義的“a”。

要解決此問題,只需在 main.cc 中刪除#include "b.cc"。 其實完全去掉b.cc,因為沒有任何意義。

如果您真的想這樣做,請使用 extern int a 為名為 ah 的“a”創建一個單獨的 header。 那么main.cc和b.cc就可以隨意包含ah而不需要重新定義a。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM