【C++】手写一个shared_ptr(约264字)

首先回顾一下shared_ptr的概念

  • shared_ptr将一个计数器与类指向的对象相关联,引用计数跟踪该类有多少个对象共享同一指针。每次创建类的新对象时,初始化指针并将引用计数置为1;
  • 当对象作为另一对象的副本而创建时,拷贝构造函数拷贝指针并增加与之相应的引用计数;
  • 对一个对象进行赋值时,赋值操作符减少左操作数所指对象的引用计数(如果引用计数为减至0,则删除对象),并增加右操作数所指对象的引用计数;
  • 调用析构函数时,构造函数减少引用计数(如果引用计数减至0,则自动删除所指向的堆内存)。

智能指针shared_ptr代码实现

cpp
template
class SharedPtr
{
public:
    explicit SharedPtr();
    explicit SharedPtr(T *_ptr);
    SharedPtr(const SharedPtr& p);  // 拷贝构造函数
    ~SharedPtr();

    // 拷贝赋值运算符(左边的值减少,右边的值增加)
    SharedPtr& operator=(const SharedPtr& p);

    // 解引用运算符
    T& operator*();
    // 箭头运算符
    T* operator->();
    // 重载布尔值操作
    operator bool();

    T* get() const;

    size_t use_count();

    bool unique();

    void swap(SharedPtr& p);

private:
    size_t *count;
    T *ptr;
};

template
SharedPtr::SharedPtr() : count(new size_t(0)), ptr(nullptr)
{}

template
SharedPtr::SharedPtr(T *_ptr) : count(new size_t(1)), ptr(_ptr)
{}

template
SharedPtr::~SharedPtr()
{
    --(*count);
    if(*count <= 0) {
        delete ptr;
        delete count;
        ptr = nullptr;
        count = nullptr;
    }
    std::cout << "shared ptr destory." << std::endl;
}

template
SharedPtr::SharedPtr(const SharedPtr &p)
{
    count = p.count;
    ptr = p.ptr;
    ++(*count);
}

template
SharedPtr& SharedPtr::operator=(const SharedPtr &p)
{
    // 如果是原指针,直接返回
    if(ptr == p.ptr) {
        return *this;
    }

    if(ptr) {
        --(*count);
        if((*count) == 0) {
            delete ptr;
            delete count;
        }
    }

    ptr = p.ptr;
    count = p.count;
    ++(*count);
    return *this;
}

template
T& SharedPtr::operator*()
{
    return *ptr;
}

template
T* SharedPtr::operator->()
{
    return ptr;
}

template
SharedPtr::operator bool()
{
    return ptr != nullptr;
}

template
T* SharedPtr::get() const
{
    return ptr;
}

template
size_t SharedPtr::use_count()
{
    return *count;
}

template
bool SharedPtr::unique()
{
    return *count == 1;
}

template
void SharedPtr::swap(SharedPtr& p)
{
    std::swap(*this, p);
}

THE END
喜欢就支持一下吧
点赞0 分享
评论 抢沙发

请登录后发表评论

    暂无评论内容