C++自写list类

文章目录

成员变量

1._head指向头节点。

2._size统计有效节点个数。

cpp 复制代码
private:
	Node* _head;
	size_t _size;   
};

创建节点

1.T是类型参数,使用模板可以存储任意类型的参数。

2._data存储数据。

3._next指向下一个节点的指针。

4._prev指向前一个节点的指针。

5.使用初始化列表进行初始化,const T& data = T(): 参数默认使用类型T的默认构造函数创建的对象。

cpp 复制代码
template<class T>
struct list_node {
	T _data;
	list_node<T>* _next;
	list_node<T>* _prev;

	list_node(const T& data = T())
		:_data(data)
		, _next(nullptr)
		, _prev(nullptr)
	{
	}
};

操作符重载

1.Ref是引用类型,可以是T&,const T&.

2.Ptr是指针类型,可以是T*,const T*.

3.Node节点类型。

4.Self迭代器的自身类型。

cpp 复制代码
template<class T,class Ref, class Ptr>
struct list_iterator {
	typedef list_node<T> Node;
	typedef list_iterator<T, Ref, Ptr> Self;
	Node* _node;

	list_iterator(Node* node)
		:_node(node)
	{}

	Ref operator*() {
		return _node->_data;
	}
	
	//返回指向数据的指针
	Ptr operator->() {
		return &(_node->_data);
	}
	Self operator++() {
		_node = _node->_next;
		return *this;
	}
	Self operator++(int) {
		_node = _node->_next;
		return *this;
	}
	Self operator--() {
		_node = _node->_prev;
		return *this;
	}

	bool operator!=(const Self& s) const {
		return _node != s._node;
	}

	bool operator==(const Self& s) const {
		return _node == s._node;
	}

	friend ostream& operator<<(ostream& out, const Self& it) {
		out << it._node_data << endl;
		return out;
	}
};

list主要函数操作实现

1.iterator定义普通迭代器操作。

2.const_iterator定义const迭代器操作。

3.begin()函数是哨兵位头节点指向的下一个位置。

4.end()函数指向哨兵位头节点。

5.在默认构造函数list()中调用empty_init()初始化空列表。

6.初始化列表构造函数目的是为了支持 list mylist = {1, 2, 3, 4}; 语法。

7.拷贝构造函数,深拷贝,不会影响原始列表。

8.操作符重载,巧妙借助了swap函数交换当前变量和临时对象啊,临时对象在函数结束时自动销毁。

9.在析构函数中,先清除所有元素,在释放头节点。

10.push_back()函数进行尾插。

11.insert()在当前迭代器的位置插入新的数据,然后返回新的迭代器的位置,防止迭代器失效。

cpp 复制代码
template<class T>
class list {
	typedef list_node<T> Node;
public:

	/*typedef list_iterator<T> iterator;
	typedef list_const_iterator<T> const_iterator;*/

	typedef list_iterator<T, T&, T*> iterator;
	typedef list_iterator<T, const T&, const T*> const_iterator;

	iterator begin() {
		iterator it(_head->_next);
		return it;
	}

	iterator end() {
		return iterator(_head);
	}

	const_iterator begin() const {
		return _head->_next;
	}

	const_iterator end() const {
		return _head;
	}

	void empty_init() {
		//传匿名对象
		_head = new Node(T());
		_head->_next = _head;
		_head->_prev = _head;
		_size = 0;
	}

	list() {
		empty_init();
	}

	list(initializer_list<T> il) {
		empty_init();
		for (auto& e : il) {
			push_back(e);
		}
	}

	//lt2(lt1) 
	list(const list<T>& lt) {
		empty_init();   //初始化lt2的头节点
		for (auto& e : lt) {
			push_back(e);
		}
	}

	//lt1 = lt3
	list<T>& operator=(list<T> lt) {
		swap(lt);
		return *this;
	}

	~list() {
		clear();
		delete _head;
		_head = nullptr;
	}

	void clear() {
		auto it = begin();
		while (it != end()) {
			it = erase(it);
		}
	}

	void swap(list<int>& lt) {
		std::swap(_head, lt._head);
		std::swap(_size, lt._size);
	}


	void push_back(const T& x) {
		Node* newnode = new Node(x);
		//尾结点
		Node* tail = _head->_prev;
		tail->_next = newnode;
		newnode->_prev = tail;
		_head->_prev = newnode;
		newnode->_next = _head;
		++_size;
	}
	void push_front(const T& x) {
		insert(begin(), x);
	}

	void pop_back() {
		Node* cur = _head->_prev;
		Node* prev = cur->_prev;
		Node* next = _head;
		prev->_next = next;
		_size--;
		erase(--end());
	}
	void pop_front() {
		erase(begin());
		_size--;
	}
	iterator insert(iterator it, const T& x) {
		Node* cur = it._node;

		Node* newnode = new Node(x);
		newnode->_next = cur;
		newnode->_prev = cur->_prev;
		cur->_prev->_next = newnode;
		cur->_prev = newnode;
		++_size;

		return newnode;
	}

	iterator erase(iterator pos) {
		assert(pos != end());
		Node* cur = pos._node;
		Node* next = cur->_next;

		cur->_prev->_next = cur->_next;
		cur->_next->_prev = cur->_prev;

		delete pos._node;
		_size--;

		return next;
	}

	size_t size() const {
		return _size;
	}

	bool empty() const {
		return _size==0;
	}

private:
	Node* _head;
	size_t _size;
};

Container容器

cpp 复制代码
template<class Container>
void printf_container(const Container& con) {
	//const iterator  迭代器本身不能修改
	//const_iterator 迭代器指向的内容不能修改
	typename Container::const_iterator it = con.begin();
	while (it != con.end()) {
		//这里使用了const_iterator迭代器,按理来说迭代器指向的内容不能修改
		//会编译错误,但是这里没有报错
		//进行了按需实例化,函数没有调用就没有检查细节
		// 
		//*it += 10;

		cout << *it << " ";
		++it;
	}
	cout << endl;
}

觉得我回答有用的话,记得点个关注哟!谢谢支持!

相关推荐
阿猿收手吧!6 小时前
【C++】异步编程:std::async终极指南
开发语言·c++
REDcker6 小时前
gRPC开发者快速入门
服务器·c++·后端·grpc
doupoa7 小时前
内存指针是什么?为什么指针还要有偏移量?
android·c++
冉佳驹7 小时前
C++ ——— 异常处理的核心机制和智能指针管理
c++·异常捕获·异常继承体与多态·重载抛异常·raii思想·智能指针shared_ptr·weak_ptr指针
C++ 老炮儿的技术栈7 小时前
Qt 编写 TcpClient 程序 详细步骤
c语言·开发语言·数据库·c++·qt·算法
yuuki2332337 小时前
【C++】继承
开发语言·c++·windows
梵刹古音7 小时前
【C++】 析构函数
开发语言·c++
wangjialelele8 小时前
Linux下的IO操作以及ext系列文件系统
linux·运维·服务器·c语言·c++·个人开发
打工哪有不疯的8 小时前
使用 MSYS2 为 Qt (MinGW 32/64位) 完美配置 OpenSSL
c++·qt