2017-08-01 78 views
0

我不認爲有任何問題指出我要找的解釋。通過引用傳遞C++,指針的向量。這裏發生了什麼?

在此示例中(ABC類中的tryme()函數),爲什麼在創建對象時將執行父級的myfunction,並將其引用直接作爲參數分配給該函數。

class parent 
{ 
public: 
     int abc; 
     parent(){}; 
     ~parent(){}; 
     virtual void myfunction(void) 
     { 
      abc = 5; 
      output("parent myfunction abc %d", abc); 
     }; 
}; 

class child :public parent 
{ 

public: 
    int abc; 
    child(int val):abc(val){}; 
    child(){}; 
    ~child(){}; 

    virtual void myfunction(void) 
    { 
     output("child myfunction abc %d", abc); 
    } 
}; 

class ABC 
{ 
     std::vector<parent *> pvec; 
     void test(parent* t) 
     { 
      pvec.pushback(t); 
     }; 

     void tryme() 
     { 
      child c1 = child(3); 
      child c2 = child(6); 

      ABC::test(&c1); <-------- this executed child - I understand 
      ABC::test(&c2); <-------- this executed child - I understand 
      ABC::test(&child(9)); <-------- this executed parent - I dont understand 
      ABC::test(&child(11));<-------- this executed parent - I dont understand 

      for each (auto it in pvec) 
      { 
        it->myfunction(); 
      } 
     } 
} 

輸出

child myfunction abc 3 
    child myfunction abc 6 
    parent myfunction abc 5 
    parent myfunction abc 5 

是什麼 child c1 = child(3); &c1;

&child(3)

感謝

之間的不同
+7

'test(&child(9));'會將一個懸掛指針存儲到臨時'child'對象,該對象在'test'返回後被銷燬。所以你在這裏面對UB。 – VTT

+2

c1和c2並不好多少​​。 – 2017-08-01 22:28:15

+0

你確定它被執行了嗎?我可以在xcode ABC :: test(&child(9))中看到警告; //獲取類型爲「child」的臨時對象的對象 –

回答

1

有幾件事......你的頭銜表明你是「通過引用傳遞」。事實上,你正在傳遞「通過指針」。

而且,當你調用

ABC::test(&c1); 

你把你的堆棧變量c1的地址,並把它傳遞給你的函數。您的數組然後存儲對象的地址。前兩個電話是可以的。

但是......當你打電話

ABC::test(&child(9)); 

您正在創建一個臨時對象,將只適用於函數調用的持續時間和通過其地址的功能,然後存儲一個「懸空「指向臨時對象的指針。

當函數調用結束時,對象被銷燬。由數組仍然保持指向現在的垃圾內存。

稍後它調用「父」函數調用的事實是完全隨機的,未定義的行爲。它可以很容易地打印出生活的意義,或者在過去的日子裏,您的顯示器被炸了。 :)

+0

哈哈..謝謝,我不確定我會理解生活的意義,但是我確定我明白了這裏的問題。再次感謝。 – legameeternoforall