模拟实现list

list是类库中的一个类,可以将其视为双向链表。


使用它的好处是在任何位置增加或删除元素都很快

缺点是不支持随机存取


话不多说,直接上代码:

代码后面都有注释,希望看完可以对你有帮助。

#include<iostream>
#include<assert.h>
#include<windows.h>
using namespace std;

#pragma once

typedef int DataType;

struct Node
{

	Node(const DataType& data)
	:_data(data)
	, _next(NULL)
	, _pre(NULL)
	{}


	DataType _data;   //值
	Node* _next;    //下一个节点
	Node* _pre;     //上一个节点
};

class List
{
public:
	List()
		:_head(NULL)
		, _tail(NULL)
		, _size(0)
	{}

	List(size_t n, const DataType& data)
	{}

	List(const List& l)
	{}


	List& operator=(const List& l)
	{
		if (this != &l)
		{
		}
		return *this;
	}


	//尾插
	void PushBack(const DataType& data)
	{
		//构造一个新的节点
		Node* _node = new Node(data);

		//链表为空
		if (NULL == _head)
		{
			_head = _tail = _node;
		}

		//链表不为空
		else
		{
			_tail->_next = _node;  //先将新节点链接到尾部
			_node->_pre = _tail;
			_tail = _tail->_next;   //将尾节点向后移
		}
		++_size;
	}


	//尾删
	void PopBack()
	{
		//链表为空直接返回
		if (_head == NULL)
			return;

		//链表中只有一个节点
		else if (_head == _tail)
		{
			delete _tail;
			_tail = _head = NULL;
		}

		//链表中有多个节点
		else
		{
			_tail = _tail->_pre;
			delete _tail->_next;
			_tail->_next = NULL;
		}
		--_size;
	}

	//头插
	void PushFront(const DataType& data)
	{
		Node* _node = new Node(data);
		if (_head == NULL)
			_head = _tail = _node;

		else
		{
			_node->_next = _head;
			_head->_pre = _node;
			_node = _head;
		}
		++_size;
	}


	//头删
	void PopFront()
	{
		//链表为空
		if (_head == NULL)
			return;

		//链表中只有一个节点
		else if (_head == _tail)
		{
			delete _head;
			_head = _tail = NULL;
		}

		//链表中有多个节点
		else
		{
			_head = _head->_next;
			delete _head->_pre;
			_head->_pre == NULL;
		}
		--_size;
	}


	//任意位置的插入
	void Insert(Node* pos, const DataType& data)
	{
		//此处需要注意assert和if检验的区别
		assert(pos);
		assert(data);
		if (pos == _tail)
		{
			//相当于尾插
			PushBack(data);
		}
		else
		{
			Node* _node = new Node(data);
			//先建立起_node pos pos->_next的三角关系
			_node->_next = pos->_next;
			pos->_next->_pre = _node;

			pos->_next = _node;
			_node->_pre = pos;
			++_size;
		}
	}


	//任意位置的删除
	void Erase(Node* pos)
	{
		assert(pos);
		if (_head == NULL)
			return;

		else if (_head == pos)
			PopFront();//头删

		else if (_tail == pos)
			PopBack();

		else
		{
			pos->_pre->_next = pos->_next;
			pos->_next->_pre = pos->_pre;
			delete pos;
			pos == NULL;
			--_size;
		}
	}


	void DestoryList()
	{
		size_t size = _size;
		while (size)
		{
			PopFront();
			--size;
		}
	}


	void Clear()
	{
		DestoryList();
		_size = 0;
	}


	void PrintList()
	{
		Node* cur = _head;
		size_t size = _size;
		while (size)
		{
 			cout << cur->_data << "";
			cur = cur->_next;
			--size;
		}
		cout << endl;
	}

	Node Front()
	{
		return *_head;
	}

	const Node Front()const
	{
		return *_head;
	}

	Node Back()
	{
		return *_tail;
	}

	const Node Back()const
	{
		return *_tail;
	}

	size_t Size()
	{
		return _size;
	}
	bool Empty()
	{
		return 0 == _size;
	}
private:
	Node* _head;
	Node* _tail;
	size_t _size;

};

测试部分只是测试了简单的头插、头删、尾插、尾删。

读者有兴趣可自行测试

 
 
void FunTest()
{
	List l;
	l.PushFront(1);
	l.PrintList();

	l.PushBack(2);
	l.PushBack(3);
	l.PushBack(4);
	l.PushBack(5);
	l.PushBack(6);
	l.PushBack(7);
	l.PushBack(8);
	l.PrintList();
 
	l.PopBack();
	l.PrintList();

	l.PopFront();
	l.PrintList();

}

int main()
{
	FunTest();
	system("pause");
	return 0;
}



猜你喜欢

转载自blog.csdn.net/weixin_36229332/article/details/78724616