2012-05-04 72 views
0

也許你可以爲我清理一些東西,因爲我不知道我的思想在哪裏存在缺陷。首先是一些代碼:指向對象的全局指針會導致訪問衝突?

Talker.h:

class talker  
{ 
    public: 
    talker(); 
    void sayHello() {cout << "Hello";} ; 
}; 

anotherClass.h:

class anotherClass 
{ 
    public: 
    anotherClass(); 
    void doSomethingYourself() { cout << "will do"; }; 
    void askHimToSayHello() { pointerToTalker->sayHello; }; 
          //Access violation, bad pointer(?) 
}; 

COMMON.H:

static talker *pointerToTalker;  
     // if I add here "= new talker", code works fine 

main.cpp中:

#include "common.h" 
int main() 
{ 
    pointerToTalker = new talker;   // Here is the bug, but why? 
    pointerToTalker -> sayHello;    // says Hello alright 

    anotherClass *pointerToAnotherClass = new anotherClass; 
    pointerToAnotherClass -> doSomething(); //Does something OK 

    pointerToAnotherClass -> askHimToSayHello(); // Causes access violation 
} 

當然函數有點複雜,每個函數都在包含「common.h」的包含.cpp文件中實現。我的問題是 - 爲什麼pointerToTalker,如果在main()中初始化,在anotherClass :: AskHimToSayHello()內不起作用?它在那裏使用的時候應該指向有效的內存。 這是我的「Hello world,OOP!」順便說一句,所以請溫柔,如果對我沒有希望:)

對不起,幼稚風格btw。它可以幫助我減少代碼,使我得到更緊湊的東西,而不會丟失大圖:)。

回答

4

因爲

static talker *pointerToTalker; 

不是全局。在這種情況下,static給出了包含common.h的每個翻譯單位(cpp文件+包含文件)的可變內部鏈接。

您需要將其聲明爲extern

extern talker *pointerToTalker; 

,並在一個單一的實現文件初始化。

聲明它static將爲每個翻譯單元創建一個pointerToTalker的副本。所以你正在初始化從main.cpp。其他人沒有初始化,因此您碰到未定義的行爲。正確的方法是:

//common.h: 
extern talker *pointerToTalker;  

//common.cpp 
#include "common.h" 
talker* pointerToTalker = new talker;