2013-04-12 91 views
2

我有兩個類,Foo和Bar。 Bar保持對Foo的引用,並且具有調用Foo中的方法來更改其狀態的方法。代碼如下所示。在Visual Studio調試模式下運行時C++對象引用損壞

class Foo 
{ 
private: 
    double m_value; 

public: 
    void setValue(double value) { 
     this->m_value = value; 
    }; 

    double getValue() { 
     return this->m_value; 
    }; 
}; 

class Bar 
{ 
private: 
    Foo& m_foo; 

public: 
    Bar() : m_foo(Foo()) { 
    }; 

    void setFooValue(double value) { 
     m_foo.setValue(value); 
    }; 

    double getFooValue() { 
     return m_foo.getValue(); 
    }; 
};  

的問題出現了,當我嘗試將它設置後訪問foo的值,如下:

Bar bar; 

bar.setFooValue(10000.0); 

double value = bar.getFooValue(); 

std::cout << "Foo value is: " << value << std::endl; 

其輸出Foo value is -9.25596e+061。看起來內存已經變得腐敗 - 爲什麼?據我所知,不存儲m_foo作爲參考(即使用Foo m_foo;)將解決這個問題,但我不明白爲什麼這也是。

更令人費解的是,上面的代碼在釋放模式下運行時按需要工作。

我正在使用Visual Studio 2010進行編譯。

非常感謝提前!

+0

這是*似乎工作*在釋放模式,而不是在調試模式應該是你具有不確定的行爲相當強的指標,並作爲答案,下面將證明,這一指標是良好的保證。 – WhozCraig

回答

1
Bar() : m_foo(Foo()) 

你正試圖從temporary初始化lvalue-reference。你不應該這樣做。在最後一個括號之後 - 對象將被銷燬,並且您將有懸掛引用。 真的,MSVC中有非標準擴展,它允許綁定臨時對象來引用。例如gcc給這種情況的錯誤test here你也可以檢查這個答案rvalue to lvalue conversion Visual Studio

1

當您創建酒吧

Bar() : m_foo(Foo()) { 
}; 

您提供參考新創建foo的實例,將走出去的範圍和權被分配到m_foo後,將被刪除。這實際上是VS c編譯器的缺陷,因爲g ++會給你和這樣的代碼錯誤,你可以在這裏看到。 http://liveworkspace.org/code/3kW04t $ 218

相關問題