2017-06-29 37 views
1

所以我有一個引用DLL的主程序(在單獨的解決方案中)。下面是設計代碼:C++靜態向量在DLL中丟失元素

//.h of DLL 

#ifdef DLL_PREPRO 
    #define DLL_LINK __declspec(dllexport) 
#else 
    #define DLL_LINK __declspec(dllimport) 
#endif 

enum MyID 
{ 
    //values here.... 
} 

DLL_LINK class MyCustomClass 
{ 
public: 
    MyID id; 
    LPCTSTR lpszApp; 
    LPCTSTR lpszKey; 
    LPCTSTR lpszDefault; 
    CString& strData; 
} 

static vector<MyCustomClass> m_customClass; //the vector in question 

DLL_LINK void InitTables(); 

//I have other custom classes that has almost similar structure to this, and with their corresponding vector 
//on the .cpp is the implementation of function InitTables() that is called by the EXE side wherein I am doing some processing on the vectors 

//.cpp on the EXE side 

void AddCustomClass(MyCustomClass c) 
{ 
    (&m_customClass)->push_back(c); 
} 

//I have another method here who populates the vector by calling AddCustomClass repeatedly 

我的問題是,在調試過程中,在EXE邊我看到越來越填充載體(我用「添加到watch'-ING每個向量做到這一點),但是當我步超過(F10)到dll端的InitTables函數,所有向量現在包含0個元素。 順便說一下,我拖動DLL的cpp文件的exe解決方案,以便能夠設置斷點。 由於使用空元素訪問這些向量會引發錯誤,因此我暫時在InitTables()函數之上放置了一個返回值。然後,當我F10再次回到在exe解決方案中的下一行時,所有的載體現在有他們的元素回

所以我的問題是,什麼是錯誤的設計/源代碼,應如何糾正?謝謝!

+0

這兩個項目是用完全相同的MSVC版本和完全相同的選項構建的嗎? MSVC不保證版本之間的C++ ABI兼容性,並且編譯選項差異也會破壞ABI。 –

+0

兩者都是在VS2010 pro中構建的,但我認爲兩者的項目屬性存在一些差異。 _Background:_之前只有1個程序 - 將其他項目中使用的部分分隔爲一個DLL。 –

+0

背景:MSVC已經改變了版本之間標準庫集合(和其他類)的內部佈局。因此,通過使用不同版本構建的模塊傳遞標準庫類可以提供您正在看到的效果。 –

回答

2

問題是,你已經使用keywork靜態在頭文件:

static vector<MyCustomClass> m_customClass; //the vector in question 

在這種情況下靜態裝置:該符號僅在當前單元是可見的。 因此,包含這個頭文件的每個.cpp文件都有自己的這個全局變量的實例!實際上,你可以有10個這個變量的實例。

也許你想是這樣的:

extern DLL_LINK vector<MyCustomClass> m_customClass; 

而且在各自的.cpp文件只需添加:

vector<MyCustomClass> m_customClass; 
+0

我試過你說的,但它給了我錯誤LNK2001無法解析的外部符號。從我的理解,它需要看到包含實際聲明的cpp文件,但在我的情況是,錯誤在DLL部分,它是什麼被引用。我應該如何處理這個問題? –

+0

抱歉忘了一個部分,請參閱答案更新。 extern只是說「它是變量的聲明」,所以它的定義丟失了。 –

+0

讓我來澄清一下:我是否應該在EXE中的cpp中extern這個DLL,還是你的意思是在DLL裏面有一些其他的cpp?我很抱歉抱歉。 –

0

static符在命名空間範圍的變量賦予變量內部聯動。從根本上說,這意味着每個.cpp文件都將擁有自己的這種變量副本。顯然不是你想要的。如果你想在DLL中定義變量但是從EXE訪問變量,它實際上必須是extern(和導出),而不是static