首页 > 代码库 > c++智能指针

c++智能指针

        记得前不久有一次面试被问到智能指针的实现,当时对智能指针只是听说但没有了解过,就乱七八糟地说了一遍。今天写了一遍智能指针,用了引用计数的概念。

        主要思想就是,用一个新类对原本需要的类型进行了一层封装,这个新类中保存了原本的对象指针和一个引用计数的指针,之所以全部用指针来保存,就是因为会出现多个新类的对象引用到同一个指针,这样的话当我们修改原本对象的内容以及引用计数时,就很天然性地保证了其他新类对象引用到的是最新的,同时,为了让我们以为新类的对象也是个“指针”,重载一下新类的“->”,和"*"操作符。下面直接上代码,不过其中用法还是有几点注意。

#include <stdlib.h>
#include <stdio.h>
#include <iostream>
#include <stdexcept>
class CTest
{
public:
	CTest()
	{
		printf("CTest::Construct function\n");
	}

	~CTest()
	{
		printf("CTest::Deconstruct function\n");
	}
	void Print()
	{
		printf("CTest:Print\n");
	}
};

template<class T>
class SmartPointer
{
public:
	SmartPointer(T* p = NULL):ptr(p),pUse(new size_t(1))
	{}
	SmartPointer(const SmartPointer& sp):ptr(sp.ptr), pUse(sp.pUse)
	{
		++*pUse;
	}
	
	SmartPointer& operator=(const SmartPointer& sp)
	{
		++*sp.pUse;
		decUse();
		pUse = sp.pUse;
		ptr = sp.ptr;
	}

	const T* operator->()const
	{
		if (ptr)
			return ptr;
		throw std::runtime_error("access null pointer");

	}

	T* operator->()
	{
		if (ptr)
			return ptr;
		throw std::runtime_error("access null pointer");
	}

	const T& operator*() const
	{
		if (ptr)
			return *ptr;
		throw std::runtime_error("access null pointer");
	}

	T& operator*()
	{
		if (ptr)
			return *ptr;
		throw std::runtime_error("access null pointer");
		//printf("access null pointer\n");
	}

	~SmartPointer()
	{
		decUse();
		printf("SmartPointer deconstruct\n");
	}
private:
	T* ptr;
	size_t* pUse;
	void decUse()
	{
		if (--*pUse == 0)
		{
			if (ptr)
				delete ptr;
			delete pUse;
			ptr = NULL;
			pUse = NULL;
		}
	}
};

int main()
{
	//correct
	SmartPointer<CTest> t(new CTest);
	t->Print();
	SmartPointer<CTest> tt(t);
	tt->Print();
	SmartPointer<CTest> ttt;
	ttt = tt;

	//wrong
	CTest* nt = new CTest;
	SmartPointer<CTest> errotT(nt);
	SmartPointer<CTest> errotT1(nt);
}

上面代码中原始类型就是CTest,这种智能指针的方法有一个限制就是同一个指针不能多次作为SmartPointer的构造函数的参数,如同main函数中最后的三局是错误的用法。

c++智能指针