實現Stack的基本操作

簡單來說,棧是一種特殊的線性表,只允許在固定一端(棧頂)進行插入和刪除元素的操作。因此棧又被稱爲後進先出的線性表。下面就來看看它可以進行哪些基本的操作。在進行擴容時,如果是對棧中基本數據類型的操作我們使用淺拷貝memcpy,否則用=進行拷貝,所以在這裏用到了類型萃取。下面看一下代碼實現。

/////////////////////實現Stack的基本操作//////////////////////
////////////////////////擴容時 類型萃取////////////////////
struct _TrueType
{
	static bool Get()
	{
		return true;
	}
};
struct _FalseType
{
	static bool Get()
	{
		return false;
	}
};
template<typename T>
struct TypeTraits
{
	typedef _FalseType IsPOD;
};
template<>
struct TypeTraits<int>
{
	typedef _TrueType IsPOD;
};
template<>
struct TypeTraits<float>
{
	typedef _TrueType IsPOD;
};
template<>
struct TypeTraits<double>
{
	typedef _TrueType IsPOD;
};
template<>
struct TypeTraits<long>
{
	typedef _TrueType IsPOD;
};
template<>
struct TypeTraits<char>
{
	typedef _TrueType IsPOD;
};
template<typename T>
class Stack
{
public:
	Stack(size_t capacity = 10)
		:_capacity(capacity)
	{
		_pData = NULL;
		_size = 0;
	}
	Stack(const Stack<T>& s)
	{
		_pData = s._pData;
		_size = s._size;
		_capacity = s._capacity;
	}
	Stack<T>& operator=(const Stack<T>& s)
	{
		if(this != &s)
		{
			_pData = s._pData;
			_size = s._size;
			_capacity = s._capacity;
		}
		return *this;
	}
	void Push(const T& x)
	{
		_CheckCapacity();
		_pData[_size++] = x;
	}
	void Pop()
	{
		assert(_size);
		--_size;
	}
	size_t Size()const
	{
		return _size;
	}
	T& Top()
	{
		return _pData[_size-1];
	}
	const T& Top()const
	{
		return _pData[_size-1];
	}
	bool Empty()const
	{
		return _size==0;
	}

private:
	void _CheckCapacity()
	{
		if(_size == capacity)
		{
			T* temp = new[_capacity*2+2];//申請空間 注意要加個常數

			if(TypeTraits<T>::IsPOD::Get())//如果爲POD類型
			{
				memcpy(temp, _pData, sizeof(T)*_size);//用memcpy拷貝元素
			}
			for(int idx = 0; idx < _size; idx++)//不是POD類型則 用for循環一個一個拷貝元素
			{
				temp[idx] = _pData[idx];
			}
			delete[] _pData;//釋放舊空間
			_pData = temp;//指向新空間
		}
		_capacity = _capacity*2+2;//容量變爲新的容量
	}
	T* _pData;
	size_t size;
	size_t capacity;
};





發佈了62 篇原創文章 · 獲贊 14 · 訪問量 5萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章