stl——模拟实现list

list 是最常用的 stl 库之一,它的底层就是一个带头的双向循环链表,所以我们在使用时也可以把它想象成这种链表。下面我们模拟实现list。
在模拟实现 list 之前,我们首先要明确 list 的迭代器。迭代器的类型有两种,第一种就是原生态的指针,例如vector的迭代器。第二种就需要我们自己来封装,因为迭代器的使用和指针类似,所以我们需要明确一下几点:
1. 对 operator*() 进行重载。
2. 对 operator->() 重载 访问其所指空间的成员。
3. 对 operator++()、operator++(int) 、operator--()、operator--(int) 进行重载。
4. 对 operator!=() 和 operator==() 进行重载。

list迭代器失效:因为list的底层结构为带头结点的双向循环链表,因此在list中进行插入时是不会导致list的迭代器失效的,只有在删除时才会失效,并且失效的只是指向被删除节点的迭代器,其他迭代器不会受到影响。

模拟实现 list:

namespace smx
{
	template<class T>
	struct ListNode
	{
		ListNode(const T& _val=T()) :prev(nullptr), next(nullptr), val(_val)
		{

		}
		ListNode<T>* prev;
		ListNode<T>* next;
		T val;
	};
	template<class T>
	class Iterator   //迭代器类
	{
	public:
		Iterator(ListNode<T>* _pNode = nullptr) :pNode(_pNode)
		{
		}
		Iterator(const Iterator<T>& it) :pNode(it.pNode)
		{
		}
		T& operator*()
		{
			return pNode->val;
		}
		T* operator->()
		{
			return &(operator*());
		}
		Iterator<T>& operator++()
		{
			pNode = pNode->next;
			return *this;
		}
		Iterator<T>& operator++(int)
		{
			Iterator<T> tmp(*this);
			pNode = pNode->next;
			return tmp;
		}
		Iterator<T>& operator--()
		{
			pNode = pNode->prev;
			return *this;
		}
		Iterator<T>& operator--(int)
		{
			Iterator<T> tmp(*this);
			pNode = pNode->prev;
			return tmp;
		}
		bool operator!=(const Iterator<T>& it)
		{
			return pNode != it.pNode;
		}
		bool operator==(const Iterator<T>& it)
		{
			return pNode == it.pNode;
		}
	private:
		ListNode<T>* pNode;
	};

	template<class T>
	class ReverseIterator //反向迭代器
	{
	public:
		ReverseIterator(ListNode<T>* _pNode = nullptr) :pNode(_pNode)
		{
		}
		ReverseIterator(const ReverseIterator<T>& rit) :pNode(rit.pNode)
		{
		}
		T& operator*()
		{
			return pNode->val;
		}
		T* operator->()
		{
			return &(operator*());
		}
		ReverseIterator<T>& operator++()
		{
			pNode = pNode->prev;
			return *this;
		}
		ReverseIterator<T>& operator++(int)
		{
			ReverseIterator<T> tmp(*this);
			pNode = pNode->prev;
			return tmp;
		}
		ReverseIterator<T>& operator--()
		{
			pNode = pNode->next;
			return *this;
		}
		ReverseIterator<T>& operator--(int)
		{
			ReverseIterator<T> tmp(*this);
			pNode = pNode->next;
			return tmp;
		}
		bool operator!=(const ReverseIterator<T>& rit)
		{
			return pNode != rit.pNode;
		}
		bool operator==(const ReverseIterator<T>& rit)
		{
			return pNode == rit.pNode;
		}
	private:
		ListNode<T>* pNode;

	};
	template<class T>
	class ConstIterator //const 迭代器
	{
	public:
		ConstIterator(ListNode<T>* _pNode = nullptr) :pNode(_pNode)
		{
		}
		ConstIterator(const ConstIterator<T>& cit) :pNode(cit.pNode)
		{
		}
		const T& operator*() const
		{
			return pNode->val;
		}
		const T* operator->() const
		{
			return &(operator*());
		}
		ConstIterator<T>& operator++()
		{
			pNode = pNode->next;
			return *this;
		}
		ConstIterator<T>& operator++(int)
		{
			ConstIterator<T> tmp(*this);
			pNode = pNode->next;
			return tmp;
		}
		ConstIterator<T>& operator--()
		{
			pNode = pNode->prev;
			return *this;
		}
		ConstIterator<T>& operator--(int)
		{
			ConstIterator<T> tmp(*this);
			pNode = pNode->prev;
			return tmp;
		}
		bool operator!=(const ConstIterator<T>& it)
		{
			return pNode != it.pNode;
		}
		bool operator==(const ConstIterator<T>& it)
		{
			return pNode == it.pNode;
		}
	private:
		ListNode<T>* pNode;
	};
	template<class T>
	class ConstReverseIterator  //反向 const迭代器
	{
	public:
		ConstReverseIterator(ListNode<T>* _pNode = nullptr) :pNode(_pNode)
		{
		}
		ConstReverseIterator(const ConstReverseIterator<T>& crit) :pNode(crit.pNode)
		{
		}
		const T& operator*() const
		{
			return pNode->val;
		}
		const T* operator->() const
		{
			return &(operator*());
		}
		ConstReverseIterator<T>& operator++()
		{
			pNode = pNode->prev;
			return *this;
		}
		ConstReverseIterator<T>& operator++(int)
		{
			ConstReverseIterator<T> tmp(*this);
			pNode = pNode->prev;
			return tmp;
		}
		ConstReverseIterator<T>& operator--()
		{
			pNode = pNode->next;
			return *this;
		}
		ConstReverseIterator<T>& operator--(int)
		{
			ConstReverseIterator<T> tmp(*this);
			pNode = pNode->next;
			return tmp;
		}
		bool operator!=(const ConstReverseIterator<T>& rit)
		{
			return pNode != rit.pNode;
		}
		bool operator==(const ConstReverseIterator<T>& rit)
		{
			return pNode == rit.pNode;
		}
	private:
		ListNode<T>* pNode;
	};

	template<class T>
	class list
	{
	public:
		typedef Iterator<T> iterator;
		typedef ReverseIterator<T> reverse_iterator;
		typedef ConstIterator<T> const_iterator;
		typedef ConstReverseIterator<T> const_reverse_iterator;
	public:
		list()
		{
			CreateHead();
		}
		list(size_t n, const T& val = T())
		{
			CreateHead();
			for (size_t i = 0; i < n; i++)
			{
				push_back(val);
			}
		}
		//template<class iterator>
		list(iterator first, iterator last)
		{
			CreateHead();
			while (first != last)
			{
				push_back(*first);
				first++;
			}
		}
		list(const_iterator first, const_iterator last)
		{
			CreateHead();
			while (first != last)
			{
				push_back(*first);
				first++;
			}
		}
		list(const list<T>& l)
		{
			CreateHead();
			list<T> tmp(l.cbegin(), l.cend());
			std::swap(this->pHead, tmp.pHead);
		}
		list<T>& operator=(const list<T>& l)
		{
			if (this != &l)
			{
				list<T> tmp(l);
				std::swap(this->pHead,tmp.pHead);
			}
			return *this;
		}
		~list()
		{
			clear();
			delete pHead;
			pHead = nullptr;
		}
		iterator begin()
		{
			return iterator(pHead->next);
		}
		iterator end()
		{
			return iterator(pHead);
		}
		reverse_iterator rbegin()
		{
			return reverse_iterator(pHead->prev);
		}
		reverse_iterator rend()
		{
			return reverse_iterator(pHead);
		}
		const_iterator cbegin() const
		{
			return const_iterator(pHead->next);
		}
		const_iterator cend() const
		{
			return const_iterator(pHead);
		}
		const_reverse_iterator crbegin() const
		{
			return const_reverse_iterator(pHead->prev);
		}
		const_reverse_iterator crend() const
		{
			return const_reverse_iterator(pHead);
		}

		size_t size() const
		{
			size_t count = 0;
			ListNode<T>* cur = pHead->next;
			while (cur != pHead)
			{
				++count;
				cur = cur->next;
			}
			return count;
		}
		bool empty() const
		{
			return pHead->next == pHead;
		}
		void resize(size_t n, const T& value = t())
		{
			size_t _size = size();
			if (_size > n)
			{
				for (size_t i = n; i < _size; i++)
				{
					pop_back();
				}
			}
			if (_size < n)
			{
				for (size_t i = _size; i < n; i++)
				{
					push_back(value);
				}
			}
		}
		T& front()
		{
			return pHead->next->val;
		}
		const T& front() const
		{
			return pHead->next->val;
		}
		T& back()
		{
			return pHead->prev->val;
		}
		const T& back() const
		{
			return pHead->prev->val;
		}
		void push_back(const T& value)
		{
			ListNode<T>* newNode = new ListNode<T>(value);
			newNode->next = pHead;
			newNode->prev = pHead->prev;

			pHead->prev->next = newNode;
			pHead->prev = newNode;

		}
		void pop_back()
		{
			ListNode<T>* cur = pHead->prev;
			if (cur != pHead)
			{
				pHead->prev = cur->prev;
				cur->prev->next = pHead;
				delete cur;
			}
		}
		void push_front(const T& value)
		{
			ListNode<T>* newNode = new ListNode<T>(value);
			newNode->prev = pHead;
			newNode->next = pHead->next;

			newNode->next->prev = newNode;
			pHead->next = newNode;
		}
		void pop_front()
		{
			ListNode<T>* cur = pHead->next;
			if (cur != pHead)
			{
				pHead->next = cur->next;
				cur->next->prev = pHead;
				delete cur;
			}
		}
		iterator insert(iterator pos, const T& value)
		{
			ListNode<T>* newNode = new ListNode<T>(value);
			ListNode<T>* cur = pos.pNode;

			newNode->next = cur;
			newNode->prev = cur->prev;
			newNode->prev->next = newNode;
			newNode->next->prev = newNode;
			return iterator(newNode);
		}
		iterator erase(iterator pos)
		{
			ListNode<T>* cur = pos.pNode;
			ListNode<T>* next = cur->next;
			cur->prev->next = cur->next;
			cur->next->prev = cur->prev;
			delete cur;
			return iterator(next);

		}
		void clear()
		{
			ListNode<T>* cur = pHead->next;
			while (cur != pHead)
			{
				pHead->next = cur->next;
				delete cur;
				cur = pHead->next;
			}
			pHead->next = pHead;
			pHead->prev = pHead;
		}



	private:
		void CreateHead()
		{
			pHead = new ListNode<T>;
			pHead->next = pHead;
			pHead->prev = pHead;
		}
		ListNode<T>* pHead;
	};
}


 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值