關於智能指針的交叉引用以及解決方法~~
智能指針的交叉引用會導致什麼問題呢??首先,先來看以下一段代碼……
class B;
class A
{
public:
shared_ptr<B> _pb;
};
class B
{
public:
shared_ptr<A> _pa;
};
int main()
{
shared_ptr<A> pa(new A);
shared_ptr<B> pb(new B);
pa->_pb = pb;
pb->_pa = pa;
return 0;
}
顯而易見,類A中有一個指向類B的shared_ ptr強類型智能指針,類B中有一個指向類A的shared_ ptr強類型智能指針
此時,有兩個強智能指針指向了對象A,對象A的引用計數爲2。也有兩個強智能指針指向了對象B,對象B的引用計數爲2。對象A與對象B的關係如圖所示
當主函數return返回後,對象A的引用計數減一變爲1,對象B的引用計數減一變爲1,此時因爲引用計數不爲0,所以不能析構對象釋放內存,程序結束造成內存泄漏
解決方法:將類A和類B中的shared_ptr強智能指針都換成weak_ptr弱智能指針
class B;
class A
{
public:
weak_ptr<B> _pb;
};
class B
{
public:
weak_ptr<A> _pa;
};
int main()
{
shared_ptr<A> pa(new A);
shared_ptr<B> pb(new B);
pa->_pb = pb;
pb->_pa = pa;
return 0;
}
weak_ptr弱智能指針,雖然有引用計數,但實際上它並不增加計數,而是隻觀察對象的引用計數,weak_ptr的引用計數指的是有多少個weak_ptr在觀察同一個shared_ptr。而shared_ptr強智能指針的引用計數是對資源的引用計數所以此時對象A的引用計數只爲1,對象B的引用計數也只爲1。此時對象A與對象B的關係如圖所示
當主函數return返回後,對象A的引用計數減一變爲0,所以正常析構對象A;對象B的引用計數減一變爲0,所以正常析構對象B,此時不會造成內存泄漏
總結:創建對象的時候用shared_ptr強智能指針,別的地方一律持有weak_ptr弱智能指針。
哈哈,是不是又發現你的程序中有一個bug,卻不知道哪裏的問題,那就趕緊檢查檢查是不是智能指針惹的禍→_→*