初次学习STL源码,很多语义尚且比较模糊,需待二次学习
源文件结构
主要的实现都在<stl_list.h>中
- 当执行#include 时,先去c++/list.h源文件中,该文件虽然没有list的定义,但引入了<bits/stl_list.h>
- 在c++/bits/stl_list.h中找到 list 的模板定义,并在同一源文件中找到其基类 _List_base以及其他支持类
源码总览
list节点基类:_List_node_base
在学习list定义前,需要先学习它的节点类(_list_node),这样之后看list类定义才会更清楚
_List_node_base类是_list_node的基类
- 定义了 _List_node_base* 类型的 _M_next 和 _M_prev两个指针
- 声明 swap(), _M_transfer(), _M_reverse(), _M_hook(), _M_unhook(), 5个成员函数
namespace __detail {//将其放在__detail这一命名空间中
_GLIBCXX_BEGIN_NAMESPACE_VERSION
//list是双向链表,不需要在意node的类型,因为所有指针都是固定的4字节(32位机)
struct _List_node_base {
_List_node_base* _M_next;//指向下一个节点
_List_node_base* _M_prev;//指向上一个节点
//1. 交换两个节点
static void swap(_List_node_base& __x, _List_node_base& __y) _GLIBCXX_USE_NOEXCEPT;
//2.
void _M_transfer(_List_node_base* const __first,
_List_node_base* const __last) _GLIBCXX_USE_NOEXCEPT;
void _M_reverse() _GLIBCXX_USE_NOEXCEPT;
void _M_hook(_List_node_base* const __position) _GLIBCXX_USE_NOEXCEPT;
void _M_unhook() _GLIBCXX_USE_NOEXCEPT;
};
_GLIBCXX_END_NAMESPACE_VERSION
} // namespace detail
list节点:_List_node
继承自_List_node_base类
- 定义了_M_data数据成员,加上父类的前后指针,就形成了一个节点
- 构造函数中使用了初始化列表,注意stl的list是具有头结点的,这个头结点中的_M_data在初始化时就要赋值
- 如果是int类型,头结点中存储链表的size
_GLIBCXX_BEGIN_NAMESPACE_CONTAINER
//An actual node in the %list.
template<typename _Tp>
struct _List_node : public __detail::_List_node_base {
_Tp _M_data;//基类中只有前后指针,这里新增了一个数据成员变量
#if __cplusplus >= 201103L//判断是C++11之后的版本
template<typename... _Args>
_List_node(_Args&&... __args) : __detail::_List_node_base(), _M_data(std::forward<_Args>(__args)...){ }
//这里在初始化列表中使用了forward转发和可变参数,用int测试了一下,_M_data被赋予了可变参数中的最后一个
//forward完美转发相关知识尚待学习,这里可以暂时当作其不存在
#endif
};
list迭代器:_List_iterator
还需要先学习list的迭代器
- 最重要的就是定义了一个 _List_node_base 指针类型的 _M_node
- 还有一些运算符重载,使得对节点的操作变成对节点的数据成员_M_data的操作
- 特别注意的是_List_node_base和_List_node两个类型的转换
template<typename _Tp>
struct _List_iterator {
//成员变量的含义在使用再介绍,可以略过先
typedef _List_iterator<_Tp> _Self;
typedef _List_node<_Tp> _Node;
typedef ptrdiff_t difference_type;
typedef std::bidirectional_iterator_tag iterator_category;
typedef _Tp value_type;
typedef _Tp* pointer;
typedef _Tp& reference;
// The only member points to the %list element.
//!!!最重要的就是定义的节点基类指针
// _M_node只有前后指针
__detail::_List_node_base* _M_node;//在_List_iterator类的最后面,这里将它放在前面方便阅读
//无参构造,:表示接初始化列表
_List_iterator() _GLIBCXX_NOEXCEPT : _M_node() { }
//有参构造,接受一个节点基类指针作为自己的 _M_node
explicit _List_iterator(__detail::_List_node_base* __x) _GLIBCXX_NOEXCEPT : _M_node(__x) { }
//返回自身,const修饰的成员函数不允许对类中成员做修改(除非是mutable)
//_Self被定义为这个迭代器的类型
_Self _M_const_cast() const _GLIBCXX_NOEXCEPT {
return *this;
}
// Must downcast from _List_node_base to _List_node to get to _M_data.
//返回当前指向的节点的数据成员,这里用static_cast强制将_List_node_base转成了_List_node
//reference代表_Tp&类型,_Node代表_List_node<_Tp>类型,
reference operator*() const _GLIBCXX_NOEXCEPT {
return static_cast<_Node*>(_M_node)->_M_data;
}
//pointer是_Tp*类型
//__addressof的目的是当存在operator&的重载时, 依然能够获得变量的地址
pointer operator->() const _GLIBCXX_NOEXCEPT {
return std::__addressof(static_cast<_Node*>(_M_node)->_M_data);
}
//是++a
_Self& operator++() _GLIBCXX_NOEXCEPT {
_M_node = _M_node->_M_next;
return *this;
}
//是a++
_Self operator++(int) _GLIBCXX_NOEXCEPT {
_Self __tmp = *this;
_M_node = _M_node->_M_next;
return __tmp;
}
_Self& operator--() _GLIBCXX_NOEXCEPT {
_M_node = _M_node->_M_prev;
return *this;
}
_Self operator--(int) _GLIBCXX_NOEXCEPT {
_Self __tmp = *this;
_M_node = _M_node->_M_prev;
return __tmp;
}
bool operator==(const _Self& __x) const _GLIBCXX_NOEXCEPT {
return _M_node == __x._M_node;
}
bool operator!=(const _Self& __x) const _GLIBCXX_NOEXCEPT {
return _M_node != __x._M_node;
}
};
list迭代器:_List_const_iterator
和_List_iterator类似,不过这里面定义大多是const 修饰类型
- 相比较于_List_node,比较重要的是多了一个接收参数为 iterator& 的拷贝构造
template<typename _Tp>
struct _List_const_iterator {
typedef _List_const_iterator<_Tp> _Self;
typedef const _List_node<_Tp> _Node;
typedef _List_iterator<_Tp> iterator;//除了这一个,其他变量和_List_iterator一样
typedef ptrdiff_t difference_type;
typedef std::bidirectional_iterator_tag iterator_category;
typedef _Tp value_type;
typedef const _Tp* pointer;
typedef const _Tp& reference;
// The only member points to the %list element.
const __detail::_List_node_base* _M_node;
_List_const_iterator() _GLIBCXX_NOEXCEPT : _M_node() { }
//有参构造函数,但接收iterator作为参数
explicit _List_const_iterator(const __detail::_List_node_base* __x)
_GLIBCXX_NOEXCEPT : _M_node(__x) { }
//拷贝构造函数
_List_const_iterator(const iterator& __x) _GLIBCXX_NOEXCEPT : _M_node(__x._M_node) { }
//将_M_node转为iterator类型,_M_node原本是_List_node对象,而其又继承自_List_node_base
iterator _M_const_cast() const _GLIBCXX_NOEXCEPT {
return iterator(const_cast<__detail::_List_node_base*>(_M_node));
}
// Must downcast from List_node_base to _List_node to get to
// _M_data.
reference operator*() const _GLIBCXX_NOEXCEPT {
return static_cast<_Node*>(_M_node)->_M_data;
}
pointer operator->() const _GLIBCXX_NOEXCEPT {
return std::__addressof(static_cast<_Node*>(_M_node)->_M_data);
}
//++和--,==和!=
_Self& operator++() _GLIBCXX_NOEXCEPT {
_M_node = _M_node->_M_next;
return *this;
}
_Self operator++(int) _GLIBCXX_NOEXCEPT {
_Self __tmp = *this;
_M_node = _M_node->_M_next;
return __tmp;
}
_Self& operator--() _GLIBCXX_NOEXCEPT {
_M_node = _M_node->_M_prev;
return *this;
}
_Self operator--(int) _GLIBCXX_NOEXCEPT {
_Self __tmp = *this;
_M_node = _M_node->_M_prev;
return __tmp;
}
bool operator==(const _Self& __x) const _GLIBCXX_NOEXCEPT { return _M_node == __x._M_node; }
bool operator!=(const _Self& __x) const _GLIBCXX_NOEXCEPT { return _M_node != __x._M_node; }
};
list基类:_List_base
定义头结点,并将左右指针指向自己。即初始化一个带头结点的,空的双向链表
- 对于 list 容器来说,需要绑定两种内存分配器,分别是节点的 List_node<_Tp>,和创建容器时传入的数据类型 <_Tp>
- _List_base 首先定义了一个 _List_impl 类型的 _M_impl。_List_impl是一个成员模板,里面主要是创建了一个 _List_node 类型的 _M_node (注意和迭代器中的_M_node是_List_node_base *类型)。这个_M_node一般是头结点
- 还定义了类似 _M_get_size() 等对 _M_impl._M_node._M_data 的增减操作
- _M_get_node()和_M_put_node分别调用分配器的allocate和deallocate分配和回收内存
- 对_List_base的构造,就是先执行_M_impl的初始化,然后调用_M_init(),使得头文件前后指针都指向自己,即一个空的双向链表
template<typename _Tp, typename _Alloc>
class _List_base{
protected:
//_Alloc模板用于获取某种类型的对象,rebind是_Alloc的成员模板
//使用traits方法,得到_List_node<_Tp>的内存分配器
typedef typename _Alloc::template rebind<_List_node<_Tp> >::other _Node_alloc_type;
typedef typename _Alloc::template rebind<_Tp>::other _Tp_alloc_type;
//返回链表长度
static size_t _S_distance(const __detail::_List_node_base* __first,
const __detail::_List_node_base* __last) {
size_t __n = 0;
while (__first != __last) {
__first = __first->_M_next;
++__n;
}
return __n;
}
//定义_List_impl,里面只有头节点,并完成对_List_base的节点内存分配器_Node_alloc_type的初始化
//_GLIBCXX_USE_CXX11_ABI == 1 表示 连接到c++新版本
struct _List_impl : public _Node_alloc_type {
#if _GLIBCXX_USE_CXX11_ABI
_List_node<size_t> _M_node;
#else
__detail::_List_node_base _M_node;
#endif
//构造函数和初始化列表
_List_impl() : _Node_alloc_type(), _M_node() { }
//拷贝构造,接收的是一个节点内存分配器
_List_impl(const _Node_alloc_type& __a) _GLIBCXX_NOEXCEPT : _Node_alloc_type(__a), _M_node() { }
#if __cplusplus >= 201103L
//构造函数,并传入一个节点分配器
_List_impl(_Node_alloc_type&& __a) _GLIBCXX_NOEXCEPT
: _Node_alloc_type(std::move(__a)), _M_node() { }
#endif
};
_List_impl _M_impl;
#if _GLIBCXX_USE_CXX11_ABI
size_t _M_get_size() const { return _M_impl._M_node._M_data; }//头结点中存储链表大小
void _M_set_size(size_t __n) { _M_impl._M_node._M_data = __n; }//设置链表大小
void _M_inc_size(size_t __n) { _M_impl._M_node._M_data += __n; }//增加链表长度
void _M_dec_size(size_t __n) { _M_impl._M_node._M_data -= __n; }//减少链表长度
size_t _M_distance(const __detail::_List_node_base* __first,//返回链表长度
const __detail::_List_node_base* __last) const {
return _S_distance(__first, __last);
}
// return the stored size
size_t _M_node_count() const { return _M_impl._M_node._M_data; }//也是返回链表长度
#else
// dummy implementations used when the size is not stored
size_t _M_get_size() const { return 0; }
void _M_set_size(size_t) { }
void _M_inc_size(size_t) { }
void _M_dec_size(size_t) { }
size_t _M_distance(const void*, const void*) const { return 0; }
// count the number of nodes
size_t _M_node_count() const {
//此时size为0,又由于是循环链表,所以实际传入的都是头结点
return _S_distance(_M_impl._M_node._M_next,
std::__addressof(_M_impl._M_node));
}
#endif
//分配一个节点和销毁一个节点
_List_node<_Tp>* _M_get_node() {
return _M_impl._Node_alloc_type::allocate(1);
}
void _M_put_node(_List_node<_Tp>* __p) _GLIBCXX_NOEXCEPT {
_M_impl._Node_alloc_type::deallocate(__p, 1);
}
public:
typedef _Alloc allocator_type;
//返回节点的分配器类型,_M_impl继承的是_Node_alloc_type
_Node_alloc_type& _M_get_Node_allocator() _GLIBCXX_NOEXCEPT {
return *static_cast<_Node_alloc_type*>(&_M_impl);
}
const _Node_alloc_type& _M_get_Node_allocator() const _GLIBCXX_NOEXCEPT {
return *static_cast<const _Node_alloc_type*>(&_M_impl);
}
//返回Tp的分配器类型(仍待学习)
_Tp_alloc_type _M_get_Tp_allocator() const _GLIBCXX_NOEXCEPT {
return _Tp_alloc_type(_M_get_Node_allocator());
}
//......
allocator_type get_allocator() const _GLIBCXX_NOEXCEPT {
return allocator_type(_M_get_Node_allocator());
}
//对_List_base初始化就是对_M_impl初始化
_List_base() : _M_impl() {
_M_init();
}
_List_base(const _Node_alloc_type& __a) _GLIBCXX_NOEXCEPT : _M_impl(__a) {
_M_init();
}
//拷贝操作
#if __cplusplus >= 201103L
_List_base(_List_base&& __x) noexcept : _M_impl(std::move(__x._M_get_Node_allocator())) {
auto* const __xnode = std::__addressof(__x._M_impl._M_node);
if (__xnode->_M_next == __xnode) _M_init();
else {
auto* const __node = std::__addressof(_M_impl._M_node);
__node->_M_next = __xnode->_M_next;
__node->_M_prev = __xnode->_M_prev;
__node->_M_next->_M_prev = __node->_M_prev->_M_next = __node;
_M_set_size(__x._M_get_size());
__x._M_init();
}
}
#endif
// This is what actually destroys the list.
~_List_base() _GLIBCXX_NOEXCEPT { _M_clear(); }//析构函数,里面调用了_M_clear释放内存空间
void _M_clear() _GLIBCXX_NOEXCEPT;//释放节点内存
// _M_init()世界上是对头结点的操作,将其左右都指向自己,表示空链表
void _M_init() _GLIBCXX_NOEXCEPT {
this->_M_impl._M_node._M_next = &this->_M_impl._M_node;
this->_M_impl._M_node._M_prev = &this->_M_impl._M_node;
_M_set_size(0);
}
};
list类:class list
继承自_List_base类,包含list常用函数的定义和实现
- 实现了常用的函数,如 push_back,emplace_back等
- 有些函数不在这里面实现,只有定义,如sort()
template<typename _Tp, typename _Alloc = std::allocator<_Tp>>//接收list类型和分配器,默认分配器是std::allocator
class list : protected _List_base<_Tp, _Alloc> {//表示继承自父类 _List_base
// concept requirements
//现在只要理解为:value_type是作为一种类型使用。它将依赖于分配器而确定,关于它的内容之后再详细学习
typedef typename _Alloc::value_type _Alloc_value_type;
/*
__glibcxx_class_requires
__glibcxx_class_requires2
这两句未找到释义
*/
__glibcxx_class_requires(_Tp, _SGIAssignableConcept)
__glibcxx_class_requires2(_Tp, _Alloc_value_type, _SameTypeConcept)
typedef _List_base<_Tp, _Alloc> _Base;
typedef typename _Base::_Tp_alloc_type _Tp_alloc_type;//父类定义,rebind绑定的list类型
typedef typename _Base::_Node_alloc_type _Node_alloc_type;//父类定义,rebind绑定的list节点类型
public:
typedef _Tp value_type;
typedef typename _Tp_alloc_type::pointer pointer;//这里和下面共4个参数来源于new_allocator类,只定义未初始化
typedef typename _Tp_alloc_type::const_pointer const_pointer;
typedef typename _Tp_alloc_type::reference reference;
typedef typename _Tp_alloc_type::const_reference const_reference;
typedef _List_iterator<_Tp> iterator;//相当于一个指针,只是它是一个类,包含了运算符重载
typedef _List_const_iterator<_Tp> const_iterator;
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;//反向遍历迭代器,++和--调换
typedef std::reverse_iterator<iterator> reverse_iterator;
typedef size_t size_type;
typedef ptrdiff_t difference_type;
typedef _Alloc allocator_type;
protected:
// Note that pointers-to-_Node's can be ctor-converted to
// iterator types.
typedef _List_node<_Tp> _Node;
//using声明,这里无实际意义
using _Base::_M_impl;
using _Base::_M_put_node;
using _Base::_M_get_node;
using _Base::_M_get_Tp_allocator;
using _Base::_M_get_Node_allocator;
//创建一个节点,分配内存和初始化,_Node是_List_node对象
#if __cplusplus < 201103L
_Node* _M_create_node(const value_type& __x) {
_Node* __p = this->_M_get_node();//分配一个节点,在父类中定义,使用了allocate()函数
__try {
//初始化数据,Tp_allocator是具体的数据类型的分配器,比如int
_M_get_Tp_allocator().construct(std::__addressof(__p->_M_data), __x);
} __catch(...) {
_M_put_node(__p);
__throw_exception_again;
}
return __p;
}
#else
template<typename... _Args>//在C++11版本后,允许可变参数模板,创建多个节点
_Node* _M_create_node(_Args&&... __args) {
_Node* __p = this->_M_get_node();
__try {
_M_get_Node_allocator().construct(__p, std::forward<_Args>(__args)...);
} __catch(...) {
_M_put_node(__p);
__throw_exception_again;
}
return __p;
}
#endif
public:
//无参构造
list()
#if __cplusplus >= 201103L
noexcept(is_nothrow_default_constructible<_Node_alloc_type>::value)
#endif
: _Base() { }
//拷贝构造
explicit list(const allocator_type& __a) _GLIBCXX_NOEXCEPT : _Base(_Node_alloc_type(__a)) { }
//有参构造,留n个空间,Called by list(n).
#if __cplusplus >= 201103L
explicit list(size_type __n) : _Base() { _M_default_initialize(__n); }//_M_default_initialize调用n次embrace_back()
//有参构造,以__value填充,push_back(__value),Called by list(n,v,a)
list(size_type __n, const value_type& __value,
const allocator_type& __a = allocator_type()) : _Base(_Node_alloc_type(__a)) {
_M_fill_initialize(__n, __value); //_M_fill_initialize调用n次push_back(_value)
}
#else
explicit list(size_type __n, const value_type& __value = value_type(),
const allocator_type& __a = allocator_type()) : _Base(_Node_alloc_type(__a)) {
_M_fill_initialize(__n, __value);
}
#endif
//拷贝构造,以迭代器的方式初始化,begin()等在后面定义,就是返回迭代器
//_M_initialize_dispatch在c++11前调用push_back,之后调用emplace_back;
list(const list& __x) : _Base(__x._M_get_Node_allocator()) {
_M_initialize_dispatch(__x.begin(), __x.end(), __false_type());
}
//在C++11中stl增加了initializer_list,它为所有容器提供了一个功能:任意长度的初始化列表
//例如:std::vector<int> arr = { 1, 2, 3, 4, 5 };就是通过initializer_list实现的
//关于initializer_list的具体实现在其他源文件中
//新的list构造函数
#if __cplusplus >= 201103L
list(list&& __x) noexcept : _Base(std::move(__x)) { }
list(initializer_list<value_type> __l,
const allocator_type& __a = allocator_type()) : _Base(_Node_alloc_type(__a)) {
_M_initialize_dispatch(__l.begin(), __l.end(), __false_type());
}
#endif
//list构造函数,但使用了std::_RequireInputIter对是否为迭代器进行检验,相关知识涉及到traits技术,暂未学习
#if __cplusplus >= 201103L
template<typename _InputIterator, typename = std::_RequireInputIter<_InputIterator>>
list(_InputIterator __first, _InputIterator __last,
const allocator_type& __a = allocator_type()) : _Base(_Node_alloc_type(__a)) {
_M_initialize_dispatch(__first, __last, __false_type());
}
#else
template<typename _InputIterator>
list(_InputIterator __first, _InputIterator __last,
const allocator_type& __a = allocator_type()) : _Base(_Node_alloc_type(__a)) {
// Check whether it's an integral type. If so, it's not an iterator.
typedef typename std::__is_integer<_InputIterator>::__type _Integral;
_M_initialize_dispatch(__first, __last, _Integral());
}
#endif
//对赋值运算符=的重载,clear是清除,swap是本类的成员函数,交换头结点和节点内存分配器
list& operator=(const list& __x);
#if __cplusplus >= 201103L
list& operator=(list&& __x) {
// NB: DR 1204.
// NB: DR 675.
this->clear();
this->swap(__x);
return *this;
}
list& operator=(initializer_list<value_type> __l) {
this->assign(__l.begin(), __l.end());//assign在后面实现复制
return *this;
}
#endif
//从这里开始是assign函数的多态
//assign函数,增加n个val值,_M_fill_assign在本文件中只找到定义,实现在list.tcc文件中,主要是调用了insert(end(), __n, __val);
void assign(size_type __n, const value_type& __val) { _M_fill_assign(__n, __val); }
#if __cplusplus >= 201103L
//assign函数,迭代器的方式添加,_M_assign_dispatch同样在list.tcc中,调用的是insert(__last1, __first2, __last2); __last1是原list的end()
template<typename _InputIterator,
typename = std::_RequireInputIter<_InputIterator>> void assign(_InputIterator __first,
_InputIterator __last) {
_M_assign_dispatch(__first, __last, __false_type());
}
#else
template<typename _InputIterator>
void assign(_InputIterator __first, _InputIterator __last) {
// Check whether it's an integral type. If so, it's not an iterator.
typedef typename std::__is_integer<_InputIterator>::__type _Integral;
_M_assign_dispatch(__first, __last, _Integral());
}
#endif
//assign函数,传入list实际上还是使用了begin()和end()
#if __cplusplus >= 201103L
void assign(initializer_list<value_type> __l) {
this->assign(__l.begin(), __l.end());
}
#endif
/// Get a copy of the memory allocation object.
allocator_type get_allocator() const _GLIBCXX_NOEXCEPT { return _Base::get_allocator(); }
//从这里开始是各种begin和end
//begin()和end(),注意end()返回的是最后一个元素的next节点,即头结点。因为这是双向链表
//因此有:++l.end() == l.begin()
//同时头结点中存储了size,因此输出(*l.end())将得到链表的大小(仅针对int类型)
iterator begin() _GLIBCXX_NOEXCEPT { return iterator(this->_M_impl._M_node._M_next); }
const_iterator begin() const _GLIBCXX_NOEXCEPT { return const_iterator(this->_M_impl._M_node._M_next); }
iterator end() _GLIBCXX_NOEXCEPT { return iterator(&this->_M_impl._M_node); }
const_iterator end() const _GLIBCXX_NOEXCEPT { return const_iterator(&this->_M_impl._M_node); }
//rbegin(),返回的l.end(),使用rbegin++实际上执行的是rbegin--
//auto it = l.rbegin();cout<<*it<<endl;cout<<*(++it)<<endl;分别输出最后一个数字和倒数第二个数字
//reverse_iterator似乎没有重写!=,详细还需要看它的代码
//rend()类似,返回的是头结点,++变成--,因此++rend()就返回最后一个数
reverse_iterator rbegin() _GLIBCXX_NOEXCEPT { return reverse_iterator(end()); }
const_reverse_iterator rbegin() const _GLIBCXX_NOEXCEPT { return const_reverse_iterator(end()); }
reverse_iterator rend() _GLIBCXX_NOEXCEPT { return reverse_iterator(begin()); }
const_reverse_iterator rend() const _GLIBCXX_NOEXCEPT { return const_reverse_iterator(begin()); }
//下面四个差不多,就是加上了const关键字
#if __cplusplus >= 201103L
const_iterator cbegin() const noexcept { return const_iterator(this->_M_impl._M_node._M_next); }
const_iterator cend() const noexcept { return const_iterator(&this->_M_impl._M_node); }
const_reverse_iterator crbegin() const noexcept { return const_reverse_iterator(end()); }
const_reverse_iterator crend() const noexcept { return const_reverse_iterator(begin()); }
#endif
//empty,size和max_size,max_size是由分配器决定的
bool empty() const _GLIBCXX_NOEXCEPT { return this->_M_impl._M_node._M_next == &this->_M_impl._M_node; }
size_type size() const _GLIBCXX_NOEXCEPT { return this->_M_node_count(); }
size_type max_size() const _GLIBCXX_NOEXCEPT { return _M_get_Node_allocator().max_size(); }
// resize
#if __cplusplus >= 201103L
void resize(size_type __new_size);
void resize(size_type __new_size, const value_type& __x);
#else
void resize(size_type __new_size, value_type __x = value_type());
#endif
// front()和back(),分别返回第一个元素和最后一个元素
reference front() _GLIBCXX_NOEXCEPT { return *begin(); }
const_reference front() const _GLIBCXX_NOEXCEPT { return *begin(); }
reference back() _GLIBCXX_NOEXCEPT {
iterator __tmp = end();
--__tmp;
return *__tmp;
}
const_reference back() const _GLIBCXX_NOEXCEPT {
const_iterator __tmp = end();
--__tmp;
return *__tmp;
}
//push_front(), emplace_front, pop_front(), push_bakc(), emplace_back(), pop_back()
//_M_insert在后面实现,里面最重要就是_M_hook,它是最基础的双向链表插入函数,就是在当前位置__position._M_node后分配一个节点,并对头结点的数据加1(这里要注意数据类型的问题)
void push_front(const value_type& __x) { this->_M_insert(begin(), __x); }
#if __cplusplus >= 201103L
void push_front(value_type&& __x) { this->_M_insert(begin(), std::move(__x)); }
//emplace_front(),它是C++11新出的特性,用到了可变参数和完美转发,还需进一步学习
//emplace_front()对于int这样的简单类型用处一般,但是对于list成员为某个对象时,它允许传入多个参数,这是push不能做到的
template<typename... _Args>
void emplace_front(_Args&&... __args) { this->_M_insert(begin(), std::forward<_Args>(__args)...); }
#endif
void pop_front() _GLIBCXX_NOEXCEPT { this->_M_erase(begin()); }
void push_back(const value_type& __x) { this->_M_insert(end(), __x); }
#if __cplusplus >= 201103L
void push_back(value_type&& __x) { this->_M_insert(end(), std::move(__x)); }
template<typename... _Args>
void emplace_back(_Args&&... __args) { this->_M_insert(end(), std::forward<_Args>(__args)...); }
#endif
void pop_back() _GLIBCXX_NOEXCEPT { this->_M_erase(iterator(this->_M_impl._M_node._M_prev)); }
// emplace和insert的声明
#if __cplusplus >= 201103L
//emplace的实现在list.tcc文件中,和_M_insert相似,不过使用了可变参数和forward转发
template<typename... _Args>
iterator emplace(const_iterator __position, _Args&&... __args);
//c++11中insert已经由emplace实现
iterator insert(const_iterator __position, const value_type& __x);
#else
iterator insert(iterator __position, const value_type& __x);
#endif
//insert的多态
#if __cplusplus >= 201103L
//insert: 使用emplace的实现
iterator insert(const_iterator __position, value_type&& __x) {
return emplace(__position, std::move(__x));
}
//insert: 将一个容器的一段插入链表中,整个链表复制
iterator insert(const_iterator __p, initializer_list<value_type> __l) {
return this->insert(__p, __l.begin(), __l.end());
}
#endif
//insert:将一个容器的一段插入链表中的实现
#if __cplusplus >= 201103L
iterator insert(const_iterator __position, size_type __n, const value_type& __x);
#else
void insert(iterator __position, size_type __n, const value_type& __x) {
list __tmp(__n, __x, get_allocator());
splice(__position, __tmp);//splice,将_tmp复制到目标链表中,并删除_tmp
}
#endif
//insert模板
#if __cplusplus >= 201103L
template<typename _InputIterator, typename = std::_RequireInputIter<_InputIterator>>
iterator insert(const_iterator __position, _InputIterator __first, _InputIterator __last);
#else
//insert模板
template<typename _InputIterator>
void insert(iterator __position, _InputIterator __first, _InputIterator __last) {
list __tmp(__first, __last, get_allocator());
splice(__position, __tmp);
}
#endif
//erase删除链表指定内容,调用的是_M_erase,里面使用的是un_hook()
iterator
#if __cplusplus >= 201103L
erase(const_iterator __position) noexcept;
#else
erase(iterator __position);
#endif
iterator
#if __cplusplus >= 201103L
erase(const_iterator __first, const_iterator __last) noexcept
#else
erase(iterator __first, iterator __last)
#endif
{
while (__first != __last)
__first = erase(__first);
return __last._M_const_cast();
}
//交换两个链表,包括头结点、size和内存分配器都要交换
void swap(list& __x) {
__detail::_List_node_base::swap(this->_M_impl._M_node, __x._M_impl._M_node);
size_t __xsize = __x._M_get_size();
__x._M_set_size(this->_M_get_size());
this->_M_set_size(__xsize);
// _GLIBCXX_RESOLVE_LIB_DEFECTS
// 431. Swapping containers with unequal allocators.
std::__alloc_swap<typename _Base::_Node_alloc_type>:: _S_do_it(_M_get_Node_allocator(),
__x._M_get_Node_allocator());
}
//_M_clear也在list.tcc文件中,其主要实现,是调用分配器的destory函数,回收所有节点,但保留头结点
void clear() _GLIBCXX_NOEXCEPT {
_Base::_M_clear();
_Base::_M_init();
}
//splice():将__x复制到__position指向的地方,并删除__x
void
#if __cplusplus >= 201103L
splice(const_iterator __position, list&& __x) noexcept
#else
splice(iterator __position, list& __x)
#endif
{
if (!__x.empty()) {
_M_check_equal_allocators(__x);
//_M_transfer暂时没找到实现
this->_M_transfer(__position._M_const_cast(),
__x.begin(), __x.end());
this->_M_inc_size(__x._M_get_size());
__x._M_set_size(0);
}
}
//splice()
#if __cplusplus >= 201103L
void splice(const_iterator __position, list& __x) noexcept { splice(__position, std::move(__x)); }
#endif
//splice():实现
#if __cplusplus >= 201103L
void splice(const_iterator __position, list&& __x, const_iterator __i) noexcept
#else
void splice(iterator __position, list& __x, iterator __i)
#endif
{
iterator __j = __i._M_const_cast();
++__j;
if (__position == __i || __position == __j)
return;
if (this != &__x)
_M_check_equal_allocators(__x);
this->_M_transfer(__position._M_const_cast(), __i._M_const_cast(), __j);
this->_M_inc_size(1);
__x._M_dec_size(1);
}
#if __cplusplus >= 201103L
void splice(const_iterator __position, list& __x, const_iterator __i) noexcept {
splice(__position, std::move(__x), __i);
}
#endif
#if __cplusplus >= 201103L
void splice(const_iterator __position, list&& __x, const_iterator __first,
const_iterator __last) noexcept
#else
void splice(iterator __position, list& __x, iterator __first, iterator __last)
#endif
{
if (__first != __last) {
if (this != &__x)
_M_check_equal_allocators(__x);
size_t __n = this->_M_distance(__first._M_node, __last._M_node);
this->_M_inc_size(__n);
__x._M_dec_size(__n);//会删除原链表的这一部分
this->_M_transfer(__position._M_const_cast(),
__first._M_const_cast(),
__last._M_const_cast());
}
}
#if __cplusplus >= 201103L
void splice(const_iterator __position, list& __x, const_iterator __first,
const_iterator __last) noexcept {
splice(__position, std::move(__x), __first, __last);
}
#endif
void remove(const _Tp& __value);
template<typename _Predicate>
void remove_if(_Predicate);
void unique();
template<typename _BinaryPredicate>
void unique(_BinaryPredicate);
#if __cplusplus >= 201103L
void merge(list&& __x);
void merge(list& __x) { merge(std::move(__x)); }
#else
void merge(list& __x);
#endif
#if __cplusplus >= 201103L
template<typename _StrictWeakOrdering>
void
merge(list&& __x, _StrictWeakOrdering __comp);
template<typename _StrictWeakOrdering>
void
merge(list& __x, _StrictWeakOrdering __comp)
{ merge(std::move(__x), __comp); }
#else
template<typename _StrictWeakOrdering>
void
merge(list& __x, _StrictWeakOrdering __comp);
#endif
void reverse() _GLIBCXX_NOEXCEPT { this->_M_impl._M_node._M_reverse(); }
void sort();
template<typename _StrictWeakOrdering>
void sort(_StrictWeakOrdering);
protected:
template<typename _Integer>
void _M_initialize_dispatch(_Integer __n, _Integer __x, __true_type) {
_M_fill_initialize(static_cast<size_type>(__n), __x);
}
// Called by the range constructor to implement [23.1.1]/9
template<typename _InputIterator>
void _M_initialize_dispatch(_InputIterator __first, _InputIterator __last, __false_type) {
for (; __first != __last; ++__first)
#if __cplusplus >= 201103L
emplace_back(*__first);
#else
push_back(*__first);
#endif
}
// Called by list(n,v,a), and the range constructor when it turns out
// to be the same thing.
void _M_fill_initialize(size_type __n, const value_type& __x) {
for (; __n; --__n)
push_back(__x);
}
#if __cplusplus >= 201103L
// Called by list(n).
void _M_default_initialize(size_type __n) {
for (; __n; --__n)
emplace_back();
}
// Called by resize(sz).
void _M_default_append(size_type __n);
#endif
// _GLIBCXX_RESOLVE_LIB_DEFECTS
// 438. Ambiguity in the "do the right thing" clause
template<typename _Integer>
void _M_assign_dispatch(_Integer __n, _Integer __val, __true_type) { _M_fill_assign(__n, __val); }
// Called by the range assign to implement [23.1.1]/9
template<typename _InputIterator>
void _M_assign_dispatch(_InputIterator __first, _InputIterator __last, __false_type);
// Called by assign(n,t), and the range assign when it turns out
// to be the same thing.
void _M_fill_assign(size_type __n, const value_type& __val);
// Moves the elements from [first,last) before position.
void _M_transfer(iterator __position, iterator __first, iterator __last) {
__position._M_node->_M_transfer(__first._M_node, __last._M_node);
}
// Inserts new element at position given and with value given.
#if __cplusplus < 201103L
void _M_insert(iterator __position, const value_type& __x) {
_Node* __tmp = _M_create_node(__x);
__tmp->_M_hook(__position._M_node);//_M_hook()!!
this->_M_inc_size(1);
}
#else
template<typename... _Args>
void _M_insert(iterator __position, _Args&&... __args) {
_Node* __tmp = _M_create_node(std::forward<_Args>(__args)...);
__tmp->_M_hook(__position._M_node);
this->_M_inc_size(1);
}
#endif
// Erases element at position given.
void _M_erase(iterator __position) _GLIBCXX_NOEXCEPT {
this->_M_dec_size(1);
__position._M_node->_M_unhook();
_Node* __n = static_cast<_Node*>(__position._M_node);
#if __cplusplus >= 201103L
_M_get_Node_allocator().destroy(__n);
#else
_M_get_Tp_allocator().destroy(std::__addressof(__n->_M_data));
#endif
_M_put_node(__n);
}
// To implement the splice (and merge) bits of N1599.
void _M_check_equal_allocators(list& __x) _GLIBCXX_NOEXCEPT {
if (std::__alloc_neq<typename _Base::_Node_alloc_type>::
_S_do_it(_M_get_Node_allocator(), __x._M_get_Node_allocator()))
__builtin_abort();
}
};
_GLIBCXX_END_NAMESPACE_CXX11
其他的运算符重载函数
主要是相等、比较、赋值运算符的重载
//==和!=重载:如果传入是两个iterator,比较是是它们的_M_node是否一样(_M_node是_List_node_base*类型)
template<typename _Val>
inline bool operator==(const _List_iterator<_Val>& __x,
const _List_const_iterator<_Val>& __y) _GLIBCXX_NOEXCEPT {
return __x._M_node == __y._M_node;
}
template<typename _Val>
inline bool operator!=(const _List_iterator<_Val>& __x,
const _List_const_iterator<_Val>& __y) _GLIBCXX_NOEXCEPT {
return __x._M_node != __y._M_node;
}
//==和!=重载,如果传入的是两个list,比较的是它们的迭代器(节点指针中存放的地址)以及该节点的数据是否相等
template<typename _Tp, typename _Alloc>
inline bool operator==(const list<_Tp, _Alloc>& __x, const list<_Tp, _Alloc>& __y) {
typedef typename list<_Tp, _Alloc>::const_iterator const_iterator;
const_iterator __end1 = __x.end();
const_iterator __end2 = __y.end();
const_iterator __i1 = __x.begin();
const_iterator __i2 = __y.begin();
while (__i1 != __end1 && __i2 != __end2 && *__i1 == *__i2) {
++__i1;
++__i2;
}
return __i1 == __end1 && __i2 == __end2;
}
template<typename _Tp, typename _Alloc>
inline bool operator!=(const list<_Tp, _Alloc>& __x, const list<_Tp, _Alloc>& __y) {
return !(__x == __y);
}
//比较运算符的重载;lexicographical_compare按字典序比较两个序列,逐个比较
template<typename _Tp, typename _Alloc>
inline bool operator<(const list<_Tp, _Alloc>& __x, const list<_Tp, _Alloc>& __y) {
return std::lexicographical_compare(__x.begin(), __x.end(), __y.begin(), __y.end());
}
template<typename _Tp, typename _Alloc>
inline bool operator>(const list<_Tp, _Alloc>& __x, const list<_Tp, _Alloc>& __y) {
return __y < __x;
}
template<typename _Tp, typename _Alloc>
inline bool operator<=(const list<_Tp, _Alloc>& __x, const list<_Tp, _Alloc>& __y) {
return !(__y < __x);
}
template<typename _Tp, typename _Alloc>
inline bool operator>=(const list<_Tp, _Alloc>& __x, const list<_Tp, _Alloc>& __y) {
return !(__x < __y);
}
//swap交换,具体实现在list的成员函数中,一个是接收_M_impl._M_node,另一个是对list的节点内存分配器进行交换
template<typename _Tp, typename _Alloc>
inline void swap(list<_Tp, _Alloc>& __x, list<_Tp, _Alloc>& __y) {
__x.swap(__y);
}
其他文件:list.tcc
主要是对一些list函数的实现,包括sort、merge等
namespace std _GLIBCXX_VISIBILITY(default) {
_GLIBCXX_BEGIN_NAMESPACE_CONTAINER
//_M_clear的实现,依次删除节点,但保留头结点
//这里注意是将父类转给了子类,这样使用的原理不太明白
template<typename _Tp, typename _Alloc>
void _List_base<_Tp, _Alloc>:: _M_clear() _GLIBCXX_NOEXCEPT {
typedef _List_node<_Tp> _Node;
__detail::_List_node_base* __cur = _M_impl._M_node._M_next;
while (__cur != &_M_impl._M_node)
{
_Node* __tmp = static_cast<_Node*>(__cur);
__cur = __tmp->_M_next;
#if __cplusplus >= 201103L
_M_get_Node_allocator().destroy(__tmp);
#else
_M_get_Tp_allocator().destroy(std::__addressof(__tmp->_M_data));
#endif
_M_put_node(__tmp);
}
}
//emplace就是在指定位置请求分配节点
#if __cplusplus >= 201103L
template<typename _Tp, typename _Alloc>//这里的多个template并用,暂不了解用法
template<typename... _Args>
typename list<_Tp, _Alloc>::iterator ist<_Tp, _Alloc>::
emplace(const_iterator __position, _Args&&... __args) {
_Node* __tmp = _M_create_node(std::forward<_Args>(__args)...);
__tmp->_M_hook(__position._M_const_cast()._M_node);
this->_M_inc_size(1);
return iterator(__tmp);
}
#endif
//insert的实现,和emplace类似,只是没有使用forward和可变参数
template<typename _Tp, typename _Alloc>
typename list<_Tp, _Alloc>::iterator list<_Tp, _Alloc>::
#if __cplusplus >= 201103L
insert(const_iterator __position, const value_type& __x)
#else
insert(iterator __position, const value_type& __x)
#endif
{
_Node* __tmp = _M_create_node(__x);
__tmp->_M_hook(__position._M_const_cast()._M_node);
this->_M_inc_size(1);
return iterator(__tmp);
}
//insert,插入多个值,但是实现是先创造一个临时链表,再使用splice
#if __cplusplus >= 201103L
template<typename _Tp, typename _Alloc>
typename list<_Tp, _Alloc>::iterator list<_Tp, _Alloc>::
insert(const_iterator __position, size_type __n, const value_type& __x) {
if (__n) {
list __tmp(__n, __x, get_allocator());
iterator __it = __tmp.begin();
splice(__position, __tmp);
return __it;
}
return __position._M_const_cast();
}
//insert,同样使用splice
template<typename _Tp, typename _Alloc>
template<typename _InputIterator, typename>
typename list<_Tp, _Alloc>::iterator list<_Tp, _Alloc>::
insert(const_iterator __position, _InputIterator __first, _InputIterator __last) {
list __tmp(__first, __last, get_allocator());
if (!__tmp.empty()) {
iterator __it = __tmp.begin();
splice(__position, __tmp);
return __it;
}
return __position._M_const_cast();
}
#endif
//erase,调用的是_M_erase,后者实现具体的删除操作
template<typename _Tp, typename _Alloc>
typename list<_Tp, _Alloc>::iterator list<_Tp, _Alloc>::
#if __cplusplus >= 201103L
erase(const_iterator __position) noexcept
#else
erase(iterator __position)
#endif
{
iterator __ret = iterator(__position._M_node->_M_next);
_M_erase(__position._M_const_cast());
return __ret;
}
//_M_default_append,调用emplace_back()函数
#if __cplusplus >= 201103L
template<typename _Tp, typename _Alloc>
void list<_Tp, _Alloc>:: _M_default_append(size_type __n) {
size_type __i = 0;
__try {
for (; __i < __n; ++__i)
emplace_back();
} __catch(...) {
for (; __i; --__i)
pop_back();
__throw_exception_again;
}
}
//resize,有size变大和变小两种情况,变小时需要erase多的部分,多时要emplace_back()
template<typename _Tp, typename _Alloc>
void list<_Tp, _Alloc>:: resize(size_type __new_size) {
iterator __i = begin();
size_type __len = 0;
for (; __i != end() && __len < __new_size; ++__i, ++__len)
;
if (__len == __new_size)//size变小
erase(__i, end());
else // __i == end()
_M_default_append(__new_size - __len);//size变大
}
//resize,但以固定值填充,变多时使用insert,但insert底部又用到emplace
template<typename _Tp, typename _Alloc>
void list<_Tp, _Alloc>::resize(size_type __new_size, const value_type& __x) {
iterator __i = begin();
size_type __len = 0;
for (; __i != end() && __len < __new_size; ++__i, ++__len)
;
if (__len == __new_size)
erase(__i, end());
else // __i == end()
insert(end(), __new_size - __len, __x);
}
#else//c++11之前的版本
template<typename _Tp, typename _Alloc>
void list<_Tp, _Alloc>:: resize(size_type __new_size, value_type __x) {
iterator __i = begin();
size_type __len = 0;
for (; __i != end() && __len < __new_size; ++__i, ++__len)
;
if (__len == __new_size)
erase(__i, end());
else // __i == end()
insert(end(), __new_size - __len, __x);
}
#endif
//赋值运算符的重载,将一个list复制到另一个list之上
template<typename _Tp, typename _Alloc>
list<_Tp, _Alloc>& list<_Tp, _Alloc>:: operator=(const list& __x) {
if (this != &__x) {
iterator __first1 = begin();
iterator __last1 = end();
const_iterator __first2 = __x.begin();
const_iterator __last2 = __x.end();
for (; __first1 != __last1 && __first2 != __last2;
++__first1, ++__first2)
*__first1 = *__first2;
if (__first2 == __last2)
erase(__first1, __last1);
else
insert(__last1, __first2, __last2);
}
return *this;
}
//_M_fill_assign,尾部插入
template<typename _Tp, typename _Alloc>
void list<_Tp, _Alloc>::_M_fill_assign(size_type __n, const value_type& __val) {
iterator __i = begin();
for (; __i != end() && __n > 0; ++__i, --__n)
*__i = __val;
if (__n > 0)
insert(end(), __n, __val);
else
erase(__i, end());
}
//_M_assign_dispatch,尾部插入
template<typename _Tp, typename _Alloc>
template <typename _InputIterator>
void list<_Tp, _Alloc>:: _M_assign_dispatch(_InputIterator __first2,
_InputIterator __last2, __false_type) {
iterator __first1 = begin();
iterator __last1 = end();
for (; __first1 != __last1 && __first2 != __last2;
++__first1, ++__first2)
*__first1 = *__first2;
if (__first2 == __last2)
erase(__first1, __last1);
else
insert(__last1, __first2, __last2);
}
//remove,删除指定值,有意思的是这里判断了节点数值是否和传入的数值地址一致
template<typename _Tp, typename _Alloc>
void list<_Tp, _Alloc>:: remove(const value_type& __value) {
iterator __first = begin();
iterator __last = end();
iterator __extra = __last;
while (__first != __last) {
iterator __next = __first;
++__next;
if (*__first == __value) {
if (std::__addressof(*__first) != std::__addressof(__value))
_M_erase(__first);
else
__extra = __first;
}
__first = __next;
}
if (__extra != __last)
_M_erase(__extra);
}
//unique函数,判断下一个节点是否与自己相同,如果相同,删除下一个节点
//当链表为无序时,它不能达到真正的unique效果
template<typename _Tp, typename _Alloc>
void list<_Tp, _Alloc>:: unique() {
iterator __first = begin();
iterator __last = end();
if (__first == __last)
return;
iterator __next = __first;
while (++__next != __last) {
if (*__first == *__next)
_M_erase(__next);
else
__first = __next;
__next = __first;
}
}
//merge函数,将list2加到list1上,添加时要按大小添加(适合本身已排序的list)
//例如{1, 8, 5}和{2, 4, 3}进行merge,结果是{1, 2, 4, 3, 8, 5},并且list2为空
template<typename _Tp, typename _Alloc>
void list<_Tp, _Alloc>::
#if __cplusplus >= 201103L
merge(list&& __x)
#else
merge(list& __x)
#endif
{
if (this != &__x) {
_M_check_equal_allocators(__x);
iterator __first1 = begin();
iterator __last1 = end();
iterator __first2 = __x.begin();
iterator __last2 = __x.end();
while (__first1 != __last1 && __first2 != __last2)
if (*__first2 < *__first1) {
iterator __next = __first2;
_M_transfer(__first1, __first2, ++__next);
__first2 = __next;
} else
++__first1;
if (__first2 != __last2)
_M_transfer(__last1, __first2, __last2);
this->_M_inc_size(__x._M_get_size());
__x._M_set_size(0);
}
}
//merge:_StrictWeakOrdering严格弱顺序
template<typename _Tp, typename _Alloc>
template <typename _StrictWeakOrdering>
void list<_Tp, _Alloc>::
#if __cplusplus >= 201103L
merge(list&& __x, _StrictWeakOrdering __comp)
#else
merge(list& __x, _StrictWeakOrdering __comp)
#endif
{
if (this != &__x) {
_M_check_equal_allocators(__x);
iterator __first1 = begin();
iterator __last1 = end();
iterator __first2 = __x.begin();
iterator __last2 = __x.end();
while (__first1 != __last1 && __first2 != __last2)
if (__comp(*__first2, *__first1)) {
iterator __next = __first2;
_M_transfer(__first1, __first2, ++__next);
__first2 = __next;
}
else
++__first1;
if (__first2 != __last2)
_M_transfer(__last1, __first2, __last2);
this->_M_inc_size(__x._M_get_size());
__x._M_set_size(0);
}
}
//sort函数:使用的merge实现
template<typename _Tp, typename _Alloc>
void list<_Tp, _Alloc>::sort() {
// Do nothing if the list has length 0 or 1.
if (this->_M_impl._M_node._M_next != &this->_M_impl._M_node
&& this->_M_impl._M_node._M_next->_M_next != &this->_M_impl._M_node) {
list __carry;
list __tmp[64];
list * __fill = &__tmp[0];
list * __counter;
do {
__carry.splice(__carry.begin(), *this, begin());//这里是要将头结点一起复制给carry
for(__counter = &__tmp[0]; __counter != __fill && !__counter->empty(); ++__counter) {
__counter->merge(__carry);
__carry.swap(*__counter);
}
__carry.swap(*__counter);
if (__counter == __fill)
++__fill;
}
while ( !empty() );
for (__counter = &__tmp[1]; __counter != __fill; ++__counter)
__counter->merge(*(__counter - 1));
swap( *(__fill - 1) );
}
}
//remove_if:按条件删除,_Predicate是谓词的意思
template<typename _Tp, typename _Alloc>
template <typename _Predicate>
void list<_Tp, _Alloc>::
remove_if(_Predicate __pred) {
iterator __first = begin();
iterator __last = end();
while (__first != __last)
{
iterator __next = __first;
++__next;
if (__pred(*__first))
_M_erase(__first);
__first = __next;
}
}
//unique:_BinaryPredicate二元运算,满足条件就删除
template<typename _Tp, typename _Alloc>
template <typename _BinaryPredicate>
void list<_Tp, _Alloc>:: unique(_BinaryPredicate __binary_pred) {
iterator __first = begin();
iterator __last = end();
if (__first == __last)
return;
iterator __next = __first;
while (++__next != __last) {
if (__binary_pred(*__first, *__next))
_M_erase(__next);
else
__first = __next;
__next = __first;
}
}
//sort函数:使用_StrictWeakOrdering(自定义规则)
template<typename _Tp, typename _Alloc>
template <typename _StrictWeakOrdering>
void list<_Tp, _Alloc>::sort(_StrictWeakOrdering __comp) {
// Do nothing if the list has length 0 or 1.
if (this->_M_impl._M_node._M_next != &this->_M_impl._M_node
&& this->_M_impl._M_node._M_next->_M_next != &this->_M_impl._M_node) {
list __carry;
list __tmp[64];
list * __fill = &__tmp[0];
list * __counter;
do {
__carry.splice(__carry.begin(), *this, begin());
for(__counter = &__tmp[0]; __counter != __fill && !__counter->empty(); ++__counter) {
__counter->merge(__carry, __comp);
__carry.swap(*__counter);
}
__carry.swap(*__counter);
if (__counter == __fill)
++__fill;
}
while ( !empty() );
for (__counter = &__tmp[1]; __counter != __fill; ++__counter)
__counter->merge(*(__counter - 1), __comp);
swap(*(__fill - 1));
}
}
_GLIBCXX_END_NAMESPACE_CONTAINER
} // namespace std
#endif /* _LIST_TCC */
补充的重要函数
_M_transfer
没找到_M_transfer函数,百度找到了一个版本,参考下
_M_transfer函数是内部函数,不对外暴露,它的作用是将 _first 和 _last之间的内容(包含first,不包含last)转到本链表当前位置(this)之前
void _List_node_base:: _M_transfer(_List_node_base * const __first,
_List_node_base * const __last) _GLIBCXX_USE_NOEXCEPT {
if (this != __last) {
// Remove [first, last) from its old position.
__last->_M_prev->_M_next = this;
__first->_M_prev->_M_next = __last;
this->_M_prev->_M_next = __first;
// Splice [first, last) into its new position.
_List_node_base* const __tmp = this->_M_prev;
this->_M_prev = __last->_M_prev;
__last->_M_prev = __first->_M_prev;
__first->_M_prev = __tmp;
}
}