2014-10-04 226 views
0
struct A 
{ 
    int a = 5;    //OK 
    const int b = 5;   //OK 
    static const int c = 5; //OK 
    static int d = 5;  //Error! 
} 



error: ISO C++ forbids in-class initialization of non-const static member 'A::d' 

這是爲什麼?有人能向我解釋這背後的原因嗎?爲什麼初始化非const和靜態const成員變量而不是靜態成員變量?

+0

static - 閱讀字典http://dictionary.reference.com/browse/static – 2014-10-04 05:51:33

+0

在這個問題中提供的答案:http:// stackoverflow。com/questions/20310000/error-iso-c-forbids-class-non-const-static-member的初始化 – balajeerc 2014-10-04 05:53:28

回答

1

它與存儲數據的位置有關。這裏有一個細目:

  • INT:成員變量,存儲的任何地方類實例存儲
  • const int的:同INT
  • 靜態const int的:並不需要存儲,它可以簡單地「內聯」在哪裏使用
  • static int:這必須在程序中有一個存儲位置......在哪裏?

由於static int是可變的,所以它必須存儲在某個地方的實際位置,以便程序的一部分可以修改它,而另一部分可以看到該修改。但它不能存儲在類實例中,所以它必須更像全局變量。那麼爲什麼不把它變成一個全局變量呢?那麼,類聲明通常在頭文件中,頭文件可能包含在多個翻譯單元(.cpp文件)中。所以有效的頭文件說:「有一個int ...某處。」但是存儲需要放入相應的.cpp文件中(如全局變量)。

最後,這不是關於初始化,而是存儲。你可以離開過初始化和你仍舊沒有一個有效的程序,直到您添加到您的.cpp文件:

int A::d; // initialize if you want to, default is zero 

沒有這一點,在靜態INT的引用將是不確定的和鏈接將失敗。

+0

*「static const int:不需要存儲」* < - 這是不對。如果你將一個指針指向一個靜態const成員呢?指針應該指向什麼? – cdhowie 2014-10-04 06:37:30

+0

@cdhowie:好點。最後一次我嘗試了這樣的事情,我得到了一個未定義的符號鏈接錯誤,就像你使用非const函數一樣。但是,如果您從未採用其地址或道德等價物,那麼您可能會在沒有定義存儲位置的情況下離開。我並沒有對你是否應該*做出價值判斷,而是在通用平臺上看起來可以。 – 2014-10-04 07:17:47

1

靜態const成員變量的初始化可用於整型和枚舉類型。自從第一種語言標準(C++ 98)以來,該特徵就存在於C++中。需要在積分常量表達式(即作爲編譯時常量)中使用靜態常量成員,這是該語言的一個重要特性。整數和枚舉類型被單獨列出並以這種特殊方式處理的原因是整型常量通常用於編譯時上下文中,常量不需要存儲(沒有定義)。

爲非靜態成員提供初始值設定項的功能是新增功能(對於C++ 11)。它是一個完全不同的功能,即使它在語法級別上看起來很相似。這些初始化器被用作那些未被用戶明確初始化的類成員的構建時初始化器。

換句話說,將這兩個特徵(靜態和非靜態成員的初始化器)合併在一起是不正確的。這兩個功能是完全不同的。他們基於完全無關的內部機制。你的問題基本上應用了第一個特性:非常量靜態成員怎麼不能在類中初始化?它基本上是一個C++ 98的問題,最有可能的答案是沒有任何理由以這種特殊的方式處理非常量靜態成員。非常量靜態成員按照一般規則處理:它們需要單獨的定義,並且應在定義點提供初始化程序。