2012-04-18 33 views
9

我正在寫一個Cocos2D-X遊戲,其中玩家,敵人和其他角色將他們的屬性存儲在CCMutableDictionary中,這是std::map<std::string, CCObject*>的裝飾類。字典中的值可以通過CCMutableDictionary::objectForKey(const std::string& key)方法訪問。現在在頭文件中執行const std :: string的正確方法?

,通過我的很多.cpp文件包含的頭文件,我有幾個const char * const串在字典訪問值,如:

// in Constants.h 
const char* const kAttributeX = "x"; 
const char* const kAttributeY = "y"; 

// in a .cpp file 
CCObject* x = someDictionary->objectForKey(kAttributeX); 

所以,如果指正我錯了,但是std::string的拷貝構造函數正在被調用,並且每當我使用const char* const調用上述objectForKey方法中的一個時,臨時std::string就在堆棧上,對吧?

如果是這樣,我覺得如果這些常量屬性鍵已經是std::string對象,那麼運行效率會更高。但我該怎麼做,權利的方式?

定義他們在Constants.h文件中像下面編譯罰款,但我有一種感覺,有些事情是不正確的:

// in Constants.h 
const std::string kAttributeX = "x"; 
const std::string kAttributeY = "y"; 

我的道歉,如果這個問題已經問。我似乎無法找到我在StackOverflow上尋找的確切答案。

回答

18

你寫的代碼非常好,至少你只有一個源文件中只有#includeConstants.h文件。如果您在多個源文件中使用頭文件,則會多次定義相同的變量。正確的使用頭文件中的常量是他們分成含有聲明的變量頭(Constants.h),和源文件(Constants.cpp),其中包含定義的變量

的頭文件:

#ifndef CONSTANTS_H 
#define CONSTANTS_H 

extern const std::string kAttributeX; 
extern const std::string kAttributeY; 

#endif 

源文件:

const std::string kAttributeX = "x"; 
const std::string kAttributeY = "y"; 
+0

因此,如果字符串是在.cpp文件中定義的,它們何時實際實例化? – 2012-04-18 03:39:04

+0

@NatWeiss它們將與所有其他全局變量一起實例化。 – 2012-04-18 18:26:34

+0

多次定義的變量問題是否適用於「const char * const」?我很確定它沒有,但我不明白爲什麼。是什麼賦予「const char * const」在單個位置定義的特權,包括其值(更好,IMO,特別是維護方面)? – Brent212 2015-02-06 23:09:47

2

你的第二個選項使各Va的可以在每個翻譯單元(包含頭文件的cpp文件)中創建riables,這會稍微增加代碼大小並增加一些運行時成本(在啓動期間構建所有字符串,並在進程終止期間銷燬它們)。

解決方案suggested by Joachim的作品,但我發現聲明和定義變量分開是一個拖動。我個人很討厭重複我自己,也不喜歡一遍又一遍地說同樣的事情......

我不知道在C++本身中有一個很好的解決方案,但是我所使用的編譯器都是支持類似於__declspec(selectany)的東西,以便您可以在頭文件中定義變量,並且僅實例化一個對象(而不是每個翻譯單元一個)。

__declspec(selectany) extern const std::string kAttributeX = "x"; 

(爲什麼都externconst看到this answer)。

您仍然有支付流程啓動期間所有全局變量初始化價格的缺點。這是可以接受的101%的時間(給與2%),但你可以通過使用懶惰對象來避免這種情況(我有written about something similar here)。

相關問題