list
list,是用环状双向链表实现的。具体的的内存结构如下图:
其中需要解释的地方:1.end()指向的是一空白节点,用以实现STL前闭后开区间。2.前闭后开区间:在STL迭代器中,区间里要访问的元素一般采用[iterator1,iterator2)的表示方法。
一个list类中的数据成员是怎么样的呢?如下(g++,7.2.0)
list_node *next;
list_node *prev;
alignas(size_t) unsigned char _M_storage[sizeof(size_t)];//最终大小是一个size_t的大小,这个是用来,存储链表的大小。
在g++,7.2.0,win64下,sizeof(list) = 24。
list的构造、析构与赋值
构造函数
与vector,deque类似:
构造函数类型 | 函数原型 |
---|---|
default(1) | list(); explicit list (const allocator_type& alloc); |
fill (2) | explicit list (size_type n, const allocator_type& alloc = allocator_type()); list (size_type n, const value_type& val, const allocator_type& alloc = allocator_type()); |
range (3) | template< class InputIterator> list (InputIterator first, InputIterator last, const allocator_type& alloc = allocator_type()); |
copy (4) | list (const list& x); list (const list& x, const allocator_type& alloc); |
move (5) | list (list&& x); list (list&& x, const allocator_type& alloc); |
initializer list (6) | list (initializer_list il, const allocator_type& alloc = allocator_type()); |
赋值
使用等号赋值
类型 | 函数原型 |
---|---|
copy (1) | list& operator= (const list& x); |
move (2) | list& operator= (list&& x) |
initializer list (3) | list& operator= (initializer_list il)` |
使用assgin()赋值
类型 | 函数原型 |
---|---|
range (1) | template< class InputIterator> void assign (InputIterator first, InputIterator last); |
fill (2) | void assign (size_type n, const value_type& val); |
initializer list (3) | void assign (initializer_list il); |
元素访问
at,operator[]
此为非连续空间容器,C++并没有实现这种访问方式。
front,back
Element access | 函数原型及说明 |
---|---|
front | access the first element (public member function) reference front(); const_reference front() const; |
back | access the last element (public member function) reference back(); const_reference back() const; |
迭代器
list的迭代器tag为:a bidirectional iterator to value_type。它表示list是一个双向迭代器,另外,deque与vector的迭代器为,random access iterator随机访问迭代器,它同样为双向迭代器。但是随机访问迭代器。这样区别的目的,是因为他们能实现的一些具体操作不一样。如下:
list<int> a{1,2,3};
vector<int> b{1,2,3};
auto it1 = a.begin() + 2;//错误,list<int>(bidirectional iterator)迭代器不支持这种操作
auto it2 = b.begin() + 2;//正确,vector<int>(random access iterator)迭代器支持这种操作
所有支持的操作可以在相关页面进行查询。简而言之,随机访问迭代器就像是指针一样,重载了所有指针支持的运算符,而双向迭代器,并不支持有关的跨对象访问,只能沿着前后方向一个个访问。如下能获取到list正向或反向的迭代器。
Iterators | |
---|---|
begin cbegin | returns an iterator to the beginning (public member function) iterator begin(); const_iterator begin() const; const_iterator cbegin() const;//c++11 |
end cend | returns an iterator to the end (public member function) iterator begin(); const_iterator begin() const; const_iterator cbegin() const;//c++11 |
rbegin crbegin | returns a reverse iterator to the beginning (public member function) reverse_iterator rbegin(); const_reverse_iterator rbegin() const; const_reverse_iterator crbegin() const;//c++11 |
rend crend | returns a reverse iterator to the end (public member function) reverse_iterator rend(); const_reverse_iterator rend() const; const_reverse_iterator crend() const;//c++11 |
容量及其修改
容量
Capacity | |
---|---|
empty | checks whether the container is empty (public member function) bool empty() const noexcept; |
size | returns the number of elements (public member function) size_type size() const noexcept; |
max_size | returns the maximum possible number of elements (public member function) size_type max_size() const noexcept; |
修改
Modifiers | 函数原型及其说明 |
---|---|
clear | clears the contents (public member function)除end以外获取的迭代器均失效,它会让所有其他的元素析构,只留下一个end() void clear() noexcept; |
insert | inserts elements (public member function),其返回的是指向新插入的第一个元素的迭代器,其插入的位置是,迭代器指向的元素的前面 single element (1) iterator insert (const_iterator position, const value_type& val); fill (2) iterator insert (const_iterator position, size_type n, const value_type& val); range (3) template iterator insert (const_iterator position, InputIterator first, InputIterator last); move (4) iterator insert (const_iterator position, value_type&& val); initializer list (5) iterator insert (const_iterator position, initializer_list<value_type> il); |
emplace(C++11) | constructs element in-place (public member function),在指定位置用传入参数构造一个元素,并返回指向该元素的迭代器 template <class… Args> iterator emplace (const_iterator position, Args&&… args); |
erase | erases elements (public member function),返回的是删除的最后的一个元素的后一个元素,若是最后一个便是指向end()的迭代器 iterator erase (const_iterator position); iterator erase (const_iterator first, const_iterator last); |
push_back | adds an element to the end (public member function) void push_back (const value_type& val); void push_back (value_type&& val); |
emplace_back(C++11) | constructs an element in-place at the end (public member function) template <class… Args> void emplace_back (Args&&… args); |
pop_back | removes the last element (public member function) void pop_back(); |
push_front | inserts an element to the beginning (public member function) void push_front (const value_type& val); void push_front (value_type&& val); |
emplace_front(C++11) | constructs an element in-place at the beginning (public member function) template <class… Args> void emplace_front (Args&&… args); |
pop_front | removes the first element (public member function) void pop_front(); |
resize | changes the number of elements stored (public member function) void resize (size_type n); void resize (size_type n, const value_type& val); |
swap | swaps the contents (public member function),与deque一样,无右值重载 void swap (list& x); |
操作
与vector,deque不大一样,list有它一些独有的操作。
注意:merge中的Compare comp,remove_if中的Predicate pred以及sort中的Compare comp,这些指一个函数指针或函数对象(或者叫仿函数----STL源码解析中的称呼,可以理解为一个重载了operator() 的类的对象。)
eg:
class Functor
{
public:
int operator()(int a, int b)
{
return a < b;
}
};
Operations | |
---|---|
merge | merges two sorted lists (public member function),合并两个已经排好序的链表,否则就简单的合并链表,最终不会得到排好序的链表,再者,传入的x最终将无元素。 (1)void merge (list& x); void merge (list&& x); (2)template < class Compare> void merge (list& x, Compare comp); template < class Compare > void merge (list&& x, Compare comp); |
splice | moves elements from another list (public member function)拼接两个链表 (1)entire list void splice (const_iterator position, list& x); void splice (const_iterator position, list&& x); (2)single element void splice (const_iterator position, list& x, const_iterator i); void splice (const_iterator position, list&& x, const_iterator i); (3)element range void splice (const_iterator position, list& x, const_iterator first, const_iterator last); void splice (const_iterator position, list&& x, const_iterator first, const_iterator last); |
remove remove_if | removes elements satisfying specific criteria (public member function),移除满足特定条件的元素 void remove (const value_type& val); template < class Predicate> void remove_if (Predicate pred);//Predicate为仿函数,判断是否满足这个函数的条件 |
reverse | reverses the order of the elements (public member function),反转链表。 void reverse() noexcept; |
unique | removes consecutive duplicate elements (public member function),去重。binary_pred是去重的比较,第一个相等即重复第二个可以指定重复函数。 (1) void unique(); (2) template < class BinaryPredicate > void unique (BinaryPredicate binary_pred); |
sort | sorts the elements (public member function)元素排序,第二个可以传入comp函数,来实现另类排序,比如绝对值小的。 (1) void sort(); (2)template < class Compare> void sort (Compare comp); |