2012-07-06 207 views
0

從我所瞭解的情況來看,你在.cpp文件中初始化一個靜態成員而不是在.h中的原因是這樣就沒有風險去獲得該成員的多個實例。在C++中初始化靜態成員

//Foo.h 
    #ifndef FOO_H 
    #define FOO_H 

    class Foo{ 
     static int a; 

    }; 
    int Foo::a = 95; 
    #endif 

預處理指令確保這個.h文件只編譯一次,這確保只有一個靜態成員的實例。這是可能的,而不是啓動.cpp文件中的靜態成員?

+0

.h文件根本不編譯。 Foo_H設置爲Foo.h不會被多次包含 – Andrew 2012-07-06 11:05:31

+0

[Static Data Member Initialization]的可能重複(http://stackoverflow.com/questions/11300652/static-data-member-initialization) – dasblinkenlight 2012-07-06 11:11:03

回答

4

考慮有兩個源代碼文件,a.cppb.cpp,都包含頭。由於它們是彼此獨立編譯的,所以標頭守衛將不起作用,您將以兩個對象文件a.ob.o均爲定義Foo:a結束。嘗試將它們連接在一起將會失敗。

7

不,它只能確保每個編譯單元(.cpp文件)包含Foo.h一次。不在整個項目中。你應該定義靜態成員中Foo.cpp

3

這將導致鏈接錯誤,如果頭被包含在多個.cpp文件(翻譯單元):

//a.cpp 
#include <Foo.h> 

//b.cpp 
#include <Foo.h> 

編譯後,a.obj包含Foo::ab.obj定義包含Foo::b的定義。如果試圖將這兩個文件鏈接成單個二進制文件,將會發生多重定義錯誤。

1

不,包含的警衛確保每個編譯單元最多包含一個標頭。如果你的程序有多個編譯單元(.cpp文件),包括頭文件,那麼你將最終得到Foo::a的多個定義。