这次修改主要针对如下几个问题:
(1)防止指向同一个对象的智能指针之间的意外赋值;
(2)使智能指针能够随意地放置在各种容器中,比如STL容器、数组等;
(3)能够对存放智能指针的容器进行排序、合并、切分等等操作,比如调用list.sort()或者std::sort()等算法。
修改后的代码如下:
 
    // 非侵入式引用计数器管理对象接口
template<typename _Ty>
class INonintrusiveRefcountManager {
public:
    virtual size_t      addRef() = 0;                 // return new refcount
    virtual size_t      release() = 0;                 // return new refcount
    virtual _Ty*       realObject() = 0;
    virtual const _Ty* realObject() const = 0;
};
 
template<typename _Ty>
class DefaultNonintrusiveRefcountMgr : public INonintrusiveRefcountManager<_Ty> {
public:
    typedef _Ty DataObjectType;
    explicit DefaultNonintrusiveRefcountMgr(DataObjectType *rep = NULL)
        : m_pData(rep), m_refCount(1) { }   /* 初始引用计数为 1 */
    virtual ~DefaultNonintrusiveRefcountMgr() { }
    virtual size_t addRef() { // 引用计数 +1
        ::InterlockedIncrement((long*)&m_refCount);            // WIN32 API
        return m_refCount;
    }
    virtual size_t release() { // 引用计数 -1
        ::InterlockedDecrement((long*)&m_refCount);         // WIN32 API
        if (m_refCount == 0) {
            this->_Destroy();    // 如果引用计数为 0 ,则删除实值对象
            delete this;
            return 0; // must return 0 quickly!
        }
        return m_refCount;
    }
    virtual DataObjectType* realObject() { return m_pData; }
    virtual const DataObjectType* realObject() const { return m_pData; }
protected:
    void _Destroy() {
        delete m_pData; m_pData = NULL;                     // 销毁实值对象
    }
    DataObjectType  *m_pData;
    size_t            m_refCount;
private:
         // 禁止复制和赋值
    DefaultNonintrusiveRefcountMgr(const DefaultNonintrusiveRefcountMgr<_Ty>&);
    void operator=(const DefaultNonintrusiveRefcountMgr<_Ty>&);
};
 
    // 非侵入式引用计数智能指针模板
template<
       typename _Ty, /* 实值对象类型 */
        typename RefcountManager = DefaultNonintrusiveRefcountMgr<_Ty>
>
class SmartPtr {
public:
    typedef  typename RefcountManager::DataObjectType DataObjectType;
    SmartPtr() : m_rep(NULL) { }
    explicit SmartPtr(DataObjectType *pointee) {                 // 接管
        if (pointee != NULL)
            m_rep = new RefcountManager(pointee);
        else
            m_rep = NULL;                                      // m_rep 可能为 NULL
    }
    SmartPtr(const SmartPtr<_Ty, RefcountManager>& other) { // 复制智能指针
        if ((m_rep = other.m_rep) != NULL)
            m_rep->addRef();                              // 只增引用计数
    }
    ~SmartPtr() {
        if (m_rep != NULL)
            m_rep->release();                                      // 释放拥有权
    }
         SmartPtr<_Ty, RefcountManager>& /
    operator=(const SmartPtr<_Ty, RefcountManager>& other) { // 智能指针赋值
        if (this != &other && m_rep != other.m_rep) {
                 if (m_rep != NULL && other.m_rep != NULL
                    && m_rep->realObject() == other.m_rep->realObject())
                        return (*this);
            if (m_rep != NULL)
                m_rep->release();                          // 释放原指针拥有权
    if ((m_rep = other.m_rep) != NULL)
                m_rep->addRef();                          // 只增引用计数
        }
        return (*this);
    }
    SmartPtr<_Ty, RefcountManager>& /
    operator=(DataObjectType* pointee) { // 接管
        if (m_rep != NULL && m_rep->realObject() == pointee)
            return (*this);
        RefcountManager *pTemp = NULL;
        if (pointee != NULL)
            pTemp = new RefcountManager(pointee);
        if (m_rep != NULL)
            m_rep->release();
        m_rep = pTemp;
        return (*this);
    }
    bool operator!() const
    { return ((m_rep == NULL || m_rep->realObject() == NULL) ? true : false); }
    operator void*() const
    { return (m_rep == NULL ? NULL : m_rep->realObject()); }
    DataObjectType* operator->() {
        assert(m_rep != NULL && m_rep->realObject() != NULL);
        return (m_rep->realObject());
    }
    const DataObjectType* operator->() const {
        assert(m_rep != NULL && m_rep->realObject() != NULL);
        return (m_rep->realObject());
    }
    DataObjectType& operator*() {
        assert(m_rep != NULL && m_rep->realObject() != NULL);
        return (*(m_rep->realObject()));
    }
    const DataObjectType& operator*() const {
        assert(m_rep != NULL && m_rep->realObject() != NULL);
        return (*(m_rep->realObject()));
    }
    void swap(SmartPtr<_Ty, RefcountManager>& other) {
        if (m_rep != other.m_rep)
           std::swap(m_rep, other.m_rep);
    }
    // 获得实值对象的指针
    DataObjectType* _ugly_method()
    { return (m_rep == NULL ? NULL : m_rep->realObject()); }
    const DataObjectType* _ugly_method() const
    { return (m_rep == NULL ? NULL : m_rep->realObject()); }
private:
    RefcountManager    *m_rep;
};
 
template<class T, class S>
inline bool __cdecl operator<(const SmartPtr<T, S>& left, const SmartPtr<T, S>& right)
{
    return (*left < *right);
}
template<class T, class S>
inline bool __cdecl operator==(const SmartPtr<T, S>& left, const SmartPtr<T, S>& right)
{
    return (*left == *right);
}
template<class T, class S>
inline bool __cdecl operator>(const SmartPtr<T, S>& left, const SmartPtr<T, S>& right)
{
    return (*right < *left);
}
template<class T, class S>
inline bool __cdecl operator>=(const SmartPtr<T, S>& left, const SmartPtr<T, S>& right)
{
    return !(*left < *right);
}
template<class T, class S>
inline bool __cdecl operator<=(const SmartPtr<T, S>& left, const SmartPtr<T, S>& right)
{
    return !(*right < *left);
}
template<class T, class S>
inline bool __cdecl operator!=(const SmartPtr<T, S>& left, const SmartPtr<T, S>& right)
{
    return !(*right == *left);
}
template<class T, class S>
inline void swap(SmartPtr<T, S>& left, SmartPtr<T, S>& right)
{
    left.swap(right);
}
Logo

权威|前沿|技术|干货|国内首个API全生命周期开发者社区

更多推荐