智能指针引用C ++计数

时间:2013-03-14 11:16:19

标签: c++

我正在阅读 Safe C++ ,我对引用计数有疑问。问题在下面的代码中的评论部分提供?

#include <iostream>

using namespace std;

template <typename T>class RefCountPtr {
public: 
    explicit RefCountPtr(T* p = NULL) {
            Create(p);      
    }

    RefCountPtr(const RefCountPtr<T>& rhs) {
        Copy(rhs);      
    }

    RefCountPtr<T>& operator=(const RefCountPtr<T>& rhs) {  
        if(ptr_ != rhs.ptr_) {
            Kill();         
            Copy(rhs);  
        }
        return *this;   
    }

    RefCountPtr<T>& operator=(T* p) {
        if(ptr_ != p) { 
            Kill();     
            Create(p);  
        }   
        return *this;
    }   
    ~RefCountPtr() {
        Kill();
    }
    T* Get() const {
        return ptr_; 
    }

    T* operator->() const { 
        // SCPP_TEST_ASSERT(ptr_ != NULL, "Attempt to use operator -> on NULL pointer.");   
        return ptr_;    
    }   

    T& operator* () const { 
        // SCPP_TEST_ASSERT(ptr_ != NULL, "Attempt to use operator * on NULL pointer.");
        return *ptr_;   
    }

    int GetCount() { return *count_; }
private:    
    T*  ptr_;
    int*    count_;

    void Create(T* p) { 
        ptr_ = p;   
        if(ptr_ != NULL) {
            count_ = new int;
            *count_ = 1;    
        } else {
            count_ = NULL;  
        }   
    }   

    void Copy(const RefCountPtr<T>& rhs) {  
        ptr_ = rhs.ptr_;
        count_ = rhs.count_;
        if(count_ != NULL)  
            ++(*count_);
    }   

    void Kill() {   
        if(count_ != NULL) {
            if(--(*count_) == 0) {  
                delete ptr_;    
                delete count_;  
            }   
        }   
    }
};

void main()
{

    int* pFirstInt = new int;

    RefCountPtr<int> refPointer(pFirstInt);

    cout << "count: " << refPointer.GetCount() << std::endl;

    RefCountPtr<int> refSecondPointer = refPointer; // this calls copy constructor.

    cout << "second count: " << refSecondPointer.GetCount() << std::endl;

    RefCountPtr<int> refThirdPointer;
    refThirdPointer = pFirstInt; **// Question why are we not incrementing same int pointer? How can we correct this?
                                 // If we are not incrementing same pointer why author has provided 
                                 // operator = for data type T? 
                                 // Note: As expected program is crashing while exiting as we are deleting int pointer twice.**

    std::cout << "Third pointer: " << refThirdPointer.GetCount() << std::endl;

    RefCountPtr<int> refFourthPointer;
    refFourthPointer = refSecondPointer;

    cout << "Fourth count: " << refFourthPointer.GetCount() << std::endl;

    return;
}

/*
count: 1
second count: 2
Third pointer: 1
Fourth count: 3
Press any key to continue . . .

*/

1 个答案:

答案 0 :(得分:3)

问题在于:

refThirdPointer = pFirstInt;

从已经由另一个智能指针管理的原始指针进行分配。

因此,您最终会有两个不相关的智能指针试图管理pFirstInt。它们是无关的,因为它们有各自的参考计数,并且幸福地没有意识到彼此的存在。这导致您正在观察的双重删除。