list实际上是数据结构中的带头双向循环链表
由于链表的存储方式并不是连续的内存空间,因此链表list中的迭代器只支持前移(++)和后移(--),属于双向迭代器。
官方文档:list - C++ Reference (cplusplus.com)
| 函数名 | 功能 | 
|---|---|
| list (size_type n, const value_type& val = value_type()) | 构造的list中包含n个值为val的 元素 | 
| list() | 构造空的list | 
| list (const list& x) | 拷贝构造函数 | 
| list (InputIterator first, InputIterator last) | 迭代器区间构造 | 
void test1() {         list l1;                         // 构造空的l1     list l2(4, 100);                 // l2中放4个值为100的元素     list l3(l2.begin(), l2.end());  // 用l2的[begin(), end())左闭右开的区间构造l3     list l4(l3);                    // 用l3拷贝构造l4 }    | 函数名 | 功能 | 
|---|---|
| begin+ end | 获取第一个数据位置的iterator/const_iterator,获取最后一个数据的下一个位置的iterator/const_iterator | 
| rbegin + rend | 获取最后一个数据位置的reverse_iterator,获取第一个数据前一个位置的reverse_iterator | 
| 范围for | 搭配auto实现遍历 | 
void test1() { 	list l1; 	l1.push_back(1); 	l1.push_back(2); 	l1.push_back(3); 	l1.push_back(4); 	l1.push_back(5);  	list::iterator it = l1.begin(); 	while (it != l1.end()) 	{ 		cout << *it << " "; 		++it; 	} 	cout << endl;  	for (auto e : l1) 	{ 		cout << e << " "; 	} 	cout << endl;  }  | 函数名 | 功能 | 
|---|---|
| empty | 检测list是否为空,是返回true,否则返回false | 
| size | 返回list中有效节点的个数 | 
| front | 返回list的第一个节点中值的引用 | 
| back | 返回list的最后一个节点中值的引用 | 
| resize(num) | 重新指定容器的长度为num 若容器变长,则以默认值填充新位置。 如果容器变短,则末尾超出容器长度的元素被删除。 | 
| 函数名 | 功能 | 
|---|---|
| push_front | 在list首元素前插入值为val的元素 | 
| pop_front | 删除list中第一个元素 | 
| push_back | 在list尾部插入值为val的元素 | 
| pop_back | 删除list中最后一个元素 | 
| insert | 在list position 位置中插入值为val的元素 | 
| erase | 删除list position位置的元素 | 
| swap | 交换两个list中的元素 | 
| clear | 清空list中的有效元素 | 
| remove(elem) | 删除容器中所有与elem值匹配的元素 | 
//插入和删除 void test1() { 	list L; 	//尾插 	L.push_back(10); 	L.push_back(20); 	L.push_back(30); 	//头插 	L.push_front(100); 	L.push_front(200); 	L.push_front(300); 	//尾删 	L.pop_back(); 	printList(L); 	//头删 	L.pop_front(); 	printList(L); 	//插入 	list::iterator it = L.begin(); 	L.insert(++it, 1000); 	//删除 	it = L.begin(); 	L.erase(++it); 	//移除 	L.push_back(10000); 	L.push_back(10000); 	L.push_back(10000);     // 	L.remove(10000);     //清空 	L.clear(); } //迭代器的底层不是原生指针 //迭代器分类 //单向:forward	-	++ //双向:bidirectional	-	++/-- //随机:random	-	++/--/+/- void test2() { 	list l1; 	l1.push_back(1); 	l1.push_back(2); 	l1.push_back(3); 	l1.push_back(4); 	l1.push_back(5);  	//如何在特定位置插入? 	auto it = l1.begin(); 	int k = 3; 	while (--k) 	{ 		++it; 	} 	l1.insert(it, 6); 	for (auto e : l1) 	{ 		cout << e << " "; 	} 	cout << endl; 	l1.erase(it); 	for (auto e : l1) 	{ 		cout << e << " "; 	} 	cout << endl; }   迭代器失效即迭代器所指向的节点的无效,即该节点被删除了。因为list的底层结构为带头结点的双向循环链表,因此在list中进行插入时是不会导致list的迭代器失效的,只有在删除时才会失效,并且失效的只是指向被删除节点的迭代器,其他迭代器不会受到影响。与vector类的失效不同。
template struct list_iterator { 	typedef list_node Node; 	typedef list_iterator Self; 	Node* _node;  	list_iterator(Node* node) 		:_node(node) 	{}  	Ref operator*() 	{ 		return _node->_data; 	}  	Self& operator++() 	{ 		_node = _node->_next; 		return *this; 	}  	Self& operator--() 	{ 		_node = _node->_prev; 		return *this; 	}  	Self& operator++(int) 	{ 		Self tmp = *this; 		_node = _node->_next; 		return tmp; 	}  	Self& operator--(int) 	{ 		Self tmp = *this; 		_node = _node->_prev; 		return tmp; 	}  	Ptr operator->() 	{ 		return &_node->_data;  	}  	bool operator!=(const Self& s) const 	{ 		return _node != s._node; 	}  	bool operator==(const Self& s) const 	{ 		return _node == s._node; 	} };   #pragma once #include #include  using namespace std;  namespace paradiso { 	template 	struct list_node 	{ 		T _data; 		list_node* _next; 		list_node* _prev;  		list_node(const T& data = T()) 			:_data(data) 			, _next(nullptr) 			, _prev(nullptr) 		{} 	};  	template 	struct list_iterator 	{ 		typedef list_node Node; 		typedef list_iterator Self; 		Node* _node;  		list_iterator(Node* node) 			:_node(node) 		{}  		Ref operator*() 		{ 			return _node->_data; 		}  		Self& operator++() 		{ 			_node = _node->_next; 			return *this; 		}  		Self& operator--() 		{ 			_node = _node->_prev; 			return *this; 		}  		Self& operator++(int) 		{ 			Self tmp = *this; 			_node = _node->_next; 			return tmp; 		}  		Self& operator--(int) 		{ 			Self tmp = *this; 			_node = _node->_prev; 			return tmp; 		}  		Ptr operator->() 		{ 			return &_node->_data;  		}  		bool operator!=(const Self& s) const 		{ 			return _node != s._node; 		}  		bool operator==(const Self& s) const 		{ 			return _node == s._node; 		} 	};  	template 	class list 	{ 		typedef list_node Node; 	public: 		typedef list_iterator iterator; 		typedef list_iterator const_iterator;  		iterator begin() 		{ 			return _head->_next; 		}  		iterator end() 		{ 			return _head; 		}  		const_iterator begin() const 		{ 			return _head->_next; 		}  		const_iterator end() const 		{ 			return _head; 		} 		void empty_init() 		{ 			_head = new Node; 			_head->_next = _head; 			_head->_prev = _head; 			_size = 0; 		} 		void swap(list& lt) 		{ 			std::swap(_head, lt._head); 			std::swap(_size, lt._size); 		} 		list() 		{ 			empty_init(); 		} 		list(list& lt) 		{ 			empty_init(); 			for (auto& e : lt) 			{ 				push_back(e); 			} 		} 		list& operator=(list& lt) 		{ 			swap(lt); 			return *this; 		} 		~list() 		{ 			clear; 			delete _head; 			_head = nullptr; 		} 		void clear() 		{ 			auto it = begin(); 			while (it != end()) 			{ 				it = erase(it); 				++it; 			} 		} 		void push_back(const T& x) 		{ 			Node* newnode = new Node(x); 			Node* tail = _head->_prev;  			tail->_next = newnode; 			newnode->_prev = tail; 			newnode->_next = _head; 			_head->_prev = newnode;  			++_size;  			//insert(end(), x); 		}  		void push_front(const T& x) 		{ 			insert(begin(), x); 		}  		void insert(iterator pos, const T& x) 		{ 			Node* cur = pos._node; 			Node* prev = cur->_prev;  			Node* newnode = new Node(x);  			// prev newnode cur 			newnode->_next = cur; 			cur->_prev = newnode; 			newnode->_prev = prev; 			prev->_next = newnode;  			++_size; 		}  		void pop_back() 		{ 			erase(--end()); 		}  		void pop_front() 		{ 			erase(begin()); 		}  		iterator erase(iterator pos) 		{ 			assert(pos != end());  			Node* prev = pos._node->_prev; 			Node* next = pos._node->_next;  			prev->_next = next; 			next->_prev = 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; 	}; }