deque容器源码

来源:互联网 发布:丰田 马自达知乎 编辑:程序博客网 时间:2024/06/05 03:05
// Filename:    stl_deque.h// 如果vector能满足你的需求, 那么就使用vector// 如果不得不使用deque, 那么在进行一算法(尤其是sort)操作时// 应该先把deque中的元素复制到vector中// 执行完算法再复制回去// 这样的效率往往要高于直接使用算法的效率/* * * Copyright (c) 1994 * Hewlett-Packard Company * * Permission to use, copy, modify, distribute and sell this software * and its documentation for any purpose is hereby granted without fee, * provided that the above copyright notice appear in all copies and * that both that copyright notice and this permission notice appear * in supporting documentation.  Hewlett-Packard Company makes no * representations about the suitability of this software for any * purpose.  It is provided "as is" without express or implied warranty. * * * Copyright (c) 1997 * Silicon Graphics Computer Systems, Inc. * * Permission to use, copy, modify, distribute and sell this software * and its documentation for any purpose is hereby granted without fee, * provided that the above copyright notice appear in all copies and * that both that copyright notice and this permission notice appear * in supporting documentation.  Silicon Graphics makes no * representations about the suitability of this software for any * purpose.  It is provided "as is" without express or implied warranty. *//* NOTE: This is an internal header file, included by other STL headers. *   You should not attempt to use it directly. */#ifndef __SGI_STL_INTERNAL_DEQUE_H#define __SGI_STL_INTERNAL_DEQUE_H// 特性://   对于任何的非奇异(nonsingular)的迭代器i//     i.node是map array中的某元素的地址. i.node的内容是一个指向某个结点的头的指针//     i.first == *(i.node)//     i.last  == i.first + node_size//     i.cur是一个指向[i.first, i.last)之间的指针//       注意: 这意味着i.cur永远是一个可以解引用的指针,//            即使其是一个指向结尾后元素的迭代器////   起点和终点总是非奇异(nonsingular)的迭代器.//     注意: 这意味着空deque一定有一个node, 而一个具有N个元素的deque//          (N是Buffer Size)一定有有两个nodes////   对于除了start.node和finish.node之外的每一个node, 每一个node中的元素//   都是一个初始化过的对象. 如果start.node == finish.node,//   那么[start.cur, finish.cur)都是未初始化的空间.//   否则, [start.cur, start.last)和[finish.first, finish.cur)都是初始化的对象,//   而[start.first, start.cur)和[finish.cur, finish.last)是未初始化的空间////   [map, map + map_size)是一个合法的非空区间//   [start.node, finish.node]是内含在[map, map + map_size)区间的合法区间//   一个在[map, map + map_size)区间内的指针指向一个分配过的node,//   当且仅当此指针在[start.node, finish.node]区间内// 在前一个版本的deque中, node_size被设定为定植.// 然而在这个版本中, 用户可以自定义node_size的大小.// deque有三个模板参数, 第三个参数为size_t类型, 代表每个结点内的元素数目.// 如果第三个参数被设定为0(默认值), deque使用默认结点大小//// 使用不同结点大小的唯一理由是, 你的程序需要不同的效率, 并愿意为此付出代价,// 例如, 如果你的程序中有许多deque, 但是每个deque都只包含很少的元素,// 那么你可以使用较小的node_size来进行管理, 但是会对访问操作带来效率损失//// 不幸的是, 一些编译器不能正确处理non-type template parameters;// 如果这样, 在<stl_config.h>会定义__STL_NON_TYPE_TMPL_PARAM_BUG// 如果你的编译器不幸在列, 你只能使用默认的大小, 而不能更改__STL_BEGIN_NAMESPACE#if defined(__sgi) && !defined(__GNUC__) && (_MIPS_SIM != _MIPS_SIM_ABI32)#pragma set woff 1174#endif// 这个函数是为了防止不同编译器在处理常量表达式时的Bug// 如果n != 0, 那么就返回n, 表示buffer size为使用者自定义// 如果n ==0, 就返回默认值表示buffer size,默认值计算方法如下//    如果sz(元素类型大小sizeof(type))小于512, 返回512 / sz//    否则返回1inline size_t __deque_buf_size(size_t n, size_t sz){  return n != 0 ? n : (sz < 512 ? size_t(512 / sz) : size_t(1));}// 注意这里未继承自std::iterator#ifndef __STL_NON_TYPE_TMPL_PARAM_BUGtemplate <class T, class Ref, class Ptr, size_t BufSiz>struct __deque_iterator {  typedef __deque_iterator<T, T&, T*, BufSiz>             iterator;  typedef __deque_iterator<T, const T&, const T*, BufSiz> const_iterator;  static size_t buffer_size() {return __deque_buf_size(BufSiz, sizeof(T)); }#else /* __STL_NON_TYPE_TMPL_PARAM_BUG */template <class T, class Ref, class Ptr>struct __deque_iterator {  typedef __deque_iterator<T, T&, T*>             iterator;  typedef __deque_iterator<T, const T&, const T*> const_iterator;  static size_t buffer_size() {return __deque_buf_size(0, sizeof(T)); }#endif  typedef random_access_iterator_tag iterator_category;      // STL标准强制要求  typedef T value_type;                                      // STL标准强制要求  typedef Ptr pointer;                                       // STL标准强制要求  typedef Ref reference;                                     // STL标准强制要求  typedef size_t size_type;  typedef ptrdiff_t difference_type;                         // STL标准强制要求  typedef T** map_pointer;  typedef __deque_iterator self;  // 保存容器中的结点  T* cur;       // 指向当前缓冲区中的元素  T* first;     // 当前缓冲区的起点  T* last;      // 当前缓冲区的终点////////////////////////////////////////////////////////////////////////////////// 这个是deque内存管理的关键, 其模型如下////////////////////////////////////////////////////////////////////////////////////       ---------------------------------------------// map-->|   |   |   |   |   |   | ..... |   |   |   |<------------------//       ---------------------------------------------                  |//             |                                                        |//             |                                                        |//             |   node                                                 |//             |   缓冲区buffer, 这里实际存储元素                          |//             |   ---------------------------------------------        |//             --->|   |   |   |   |   |   | ..... |   |   | X |        |//                 ---------------------------------------------        |//                   ↑       ↑                             ↑            |//             ------        |                             |            |//             |             |                             |            |//             |   -----------   ---------------------------            |//             ----|-----        |                                      |//                 |    |        |                                      |//                 |    |        |                                      |//                 |    |        |                                      |//              ---------------------------                             |//              | cur | first | end | map |------------------------------//              ---------------------------//              迭代器, 其内部维护着一个缓冲区状态////////////////////////////////////////////////////////////////////////////////  map_pointer node;  __deque_iterator(T* x, map_pointer y)    : cur(x), first(*y), last(*y + buffer_size()), node(y) {}  __deque_iterator() : cur(0), first(0), last(0), node(0) {}  __deque_iterator(const iterator& x)    : cur(x.cur), first(x.first), last(x.last), node(x.node) {}  reference operator*() const { return *cur; }#ifndef __SGI_STL_NO_ARROW_OPERATOR  // 如果编译器支持'->'则重载, 详细见我在<stl_list.h>中的剖析  pointer operator->() const { return &(operator*()); }#endif /* __SGI_STL_NO_ARROW_OPERATOR */  // 判断两个迭代器间的距离  difference_type operator-(const self& x) const  {    return difference_type(buffer_size()) * (node - x.node - 1) +      (cur - first) + (x.last - x.cur);  }////////////////////////////////////////////////////////////////////////////////// 下面重载的这些是运算符是让deque从外界看上去维护的是一段连续空间的关键!!!////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 前缀自增////////////////////////////////////////////////////////////////////////////////// 如果当前迭代器指向元素是当前缓冲区的最后一个元素,// 则将迭代器状态调整为下一个缓冲区的第一个元素////////////////////////////////////////////////////////////////////////////////// 不是当前缓冲区最后一个元素//// 执行前缀自增前的状态// first          cur                     end// ↓               ↓                       ↓// ---------------------------------------------// |   |   |   |   |   |   | ..... |   |   | X | <----- 当前缓冲区// ---------------------------------------------//// 执行完成后的状态// first              cur                 end// ↓                   ↓                   ↓// ---------------------------------------------// |   |   |   |   |   |   | ..... |   |   | X | <----- 当前缓冲区// ---------------------------------------------//////////////////////////////////////////////////////////////////////////////////// 当前元素为当前缓冲区的最后一个元素//// 执行前缀自增前的状态// first                              cur end// ↓                                   ↓   ↓// ---------------------------------------------// |   |   |   |   |   |   | ..... |   |   | X | <----- 当前缓冲区// ---------------------------------------------//// 执行完成后的状态// first                                  end// ↓                                       ↓// ---------------------------------------------// |   |   |   |   |   |   | ..... |   |   | X | <----- 下一缓冲区// ---------------------------------------------// ↑// cur//////////////////////////////////////////////////////////////////////////////////  self& operator++()  {    ++cur;    if (cur == last) {      set_node(node + 1);      cur = first;    }    return *this;  }  // 后缀自增  // 返回当前迭代器的一个副本, 并调用前缀自增运算符实现迭代器自身的自增  self operator++(int)  {    self tmp = *this;    ++*this;    return tmp;  }  // 前缀自减, 处理方式类似于前缀自增  // 如果当前迭代器指向元素是当前缓冲区的第一个元素  // 则将迭代器状态调整为前一个缓冲区的最后一个元素  self& operator--()  {    if (cur == first) {      set_node(node - 1);      cur = last;    }    --cur;    return *this;  }  self operator--(int)  {    self tmp = *this;    --*this;    return tmp;  }////////////////////////////////////////////////////////////////////////////////// 将迭代器向前移动n个元素, n可以为负//////////////////////////////////////////////////////////////////////////////////                     operator+=(difference_type n)//                                   ↓//                      offset = n + (cur - first)//                                   |//                                   |---------- offset > 0 ? &&//                                   |           移动后是否超出当前缓冲区?//               ----------------------------//           No  |                          |  Yes//               |                          |//               ↓                          |---------- offset > 0?//           cur += n;                      |//                              ----------------------------//                          Yes |                          | No//                              |                          |//                              ↓                          |//                   计算要向后移动多少个缓冲区                |//                   node_offset =                         |//                   offset / difference_type              |//                   (buffer_size());                      ↓//                              |           计算要向前移动多少个缓冲区//                              |           node_offset = -difference_type//                              |           ((-offset - 1) / buffer_size()) - 1;//                              |                          |//                              ----------------------------//                                           |//                                           |//                                           ↓//                                       调整缓冲区//                              set_node(node + node_offset);//                                    计算并调整cur指针////////////////////////////////////////////////////////////////////////////////  self& operator+=(difference_type n)  {    difference_type offset = n + (cur - first);    if (offset >= 0 && offset < difference_type(buffer_size()))      cur += n;    else {      difference_type node_offset =        offset > 0 ? offset / difference_type(buffer_size())                   : -difference_type((-offset - 1) / buffer_size()) - 1;      set_node(node + node_offset);      cur = first + (offset - node_offset * difference_type(buffer_size()));    }    return *this;  }  self operator+(difference_type n) const  {    self tmp = *this;    // 这里调用了operator +=()可以自动调整指针状态    return tmp += n;  }  // :-), 将n变为-n就可以使用operator +=()了,  // 初等数学是神奇的, 还记得我们刚学编程时求绝对值是怎么写的吗? :P  self& operator-=(difference_type n) { return *this += -n; }  self operator-(difference_type n) const {    self tmp = *this;    return tmp -= n;  }  reference operator[](difference_type n) const { return *(*this + n); }  bool operator==(const self& x) const { return cur == x.cur; }  bool operator!=(const self& x) const { return !(*this == x); }  bool operator<(const self& x) const {    return (node == x.node) ? (cur < x.cur) : (node < x.node);  }  void set_node(map_pointer new_node)  {    node = new_node;    first = *new_node;    last = first + difference_type(buffer_size());  }};#ifndef __STL_CLASS_PARTIAL_SPECIALIZATION#ifndef __STL_NON_TYPE_TMPL_PARAM_BUGtemplate <class T, class Ref, class Ptr, size_t BufSiz>inline random_access_iterator_tagiterator_category(const __deque_iterator<T, Ref, Ptr, BufSiz>&) {  return random_access_iterator_tag();}template <class T, class Ref, class Ptr, size_t BufSiz>inline T* value_type(const __deque_iterator<T, Ref, Ptr, BufSiz>&) {  return 0;}template <class T, class Ref, class Ptr, size_t BufSiz>inline ptrdiff_t* distance_type(const __deque_iterator<T, Ref, Ptr, BufSiz>&) {  return 0;}#else /* __STL_NON_TYPE_TMPL_PARAM_BUG */template <class T, class Ref, class Ptr>inline random_access_iterator_tagiterator_category(const __deque_iterator<T, Ref, Ptr>&) {  return random_access_iterator_tag();}template <class T, class Ref, class Ptr>inline T* value_type(const __deque_iterator<T, Ref, Ptr>&) { return 0; }template <class T, class Ref, class Ptr>inline ptrdiff_t* distance_type(const __deque_iterator<T, Ref, Ptr>&) {  return 0;}#endif /* __STL_NON_TYPE_TMPL_PARAM_BUG */// 其实剖析到这里就没有什么难的了, deque的运算符才是核心#endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */// See __deque_buf_size().  The only reason that the default value is 0//  is as a workaround for bugs in the way that some compilers handle//  constant expressions.template <class T, class Alloc = alloc, size_t BufSiz = 0>class deque {public:                         // Basic types  typedef T value_type;  typedef value_type* pointer;  typedef const value_type* const_pointer;  typedef value_type& reference;  typedef const value_type& const_reference;  typedef size_t size_type;  typedef ptrdiff_t difference_type;public:                         // Iterators#ifndef __STL_NON_TYPE_TMPL_PARAM_BUG  typedef __deque_iterator<T, T&, T*, BufSiz>              iterator;  typedef __deque_iterator<T, const T&, const T&, BufSiz>  const_iterator;#else /* __STL_NON_TYPE_TMPL_PARAM_BUG */  typedef __deque_iterator<T, T&, T*>                      iterator;  typedef __deque_iterator<T, const T&, const T*>          const_iterator;#endif /* __STL_NON_TYPE_TMPL_PARAM_BUG */#ifdef __STL_CLASS_PARTIAL_SPECIALIZATION  typedef reverse_iterator<const_iterator> const_reverse_iterator;  typedef reverse_iterator<iterator> reverse_iterator;#else /* __STL_CLASS_PARTIAL_SPECIALIZATION */  typedef reverse_iterator<const_iterator, value_type, const_reference,                           difference_type>          const_reverse_iterator;  typedef reverse_iterator<iterator, value_type, reference, difference_type>          reverse_iterator;#endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */protected:                      // Internal typedefs  typedef pointer* map_pointer;  // 这个提供STL标准的allocator接口, 见<stl_alloc.h>  typedef simple_alloc<value_type, Alloc> data_allocator;  typedef simple_alloc<pointer, Alloc> map_allocator;  // 获取缓冲区最大存储元素数量  static size_type buffer_size()  {    return __deque_buf_size(BufSiz, sizeof(value_type));  }  static size_type initial_map_size() { return 8; }protected:                      // Data members  iterator start;               // 起始缓冲区  iterator finish;              // 最后一个缓冲区  // 指向map, map是一个连续的空间, 其每个元素都是一个指向缓冲区的指针  // 其模型见前面的__deque_iterator  map_pointer map;  size_type map_size;   // map容量public:                         // Basic accessors  iterator begin() { return start; }  iterator end() { return finish; }  const_iterator begin() const { return start; }  const_iterator end() const { return finish; }  reverse_iterator rbegin() { return reverse_iterator(finish); }  reverse_iterator rend() { return reverse_iterator(start); }  const_reverse_iterator rbegin() const {    return const_reverse_iterator(finish);  }  const_reverse_iterator rend() const {    return const_reverse_iterator(start);  }  // 提供随机访问能力, 其调用的是迭代器重载的operator []  // 其实际地址需要进行一些列的计算, 效率有损失  reference operator[](size_type n) { return start[difference_type(n)]; }  const_reference operator[](size_type n) const {    return start[difference_type(n)];  }  reference front() { return *start; }  reference back() {    iterator tmp = finish;    --tmp;    return *tmp;  }  const_reference front() const { return *start; }  const_reference back() const {    const_iterator tmp = finish;    --tmp;    return *tmp;  }  // 当前容器拥有的元素个数, 调用迭代器重载的operator -  size_type size() const { return finish - start;; }  size_type max_size() const { return size_type(-1); }  // deque为空的时, 只有一个缓冲区  bool empty() const { return finish == start; }public:                         // Constructor, destructor.  deque()    : start(), finish(), map(0), map_size(0)  {    create_map_and_nodes(0);  }  // 注: commit or rollback  deque(const deque& x)    : start(), finish(), map(0), map_size(0)  {    create_map_and_nodes(x.size());    __STL_TRY {      uninitialized_copy(x.begin(), x.end(), start);  // <stl_uninitialized.h>    }    __STL_UNWIND(destroy_map_and_nodes());  }  deque(size_type n, const value_type& value)    : start(), finish(), map(0), map_size(0)  {    fill_initialize(n, value);  }  deque(int n, const value_type& value)    : start(), finish(), map(0), map_size(0)  {    fill_initialize(n, value);  }  deque(long n, const value_type& value)    : start(), finish(), map(0), map_size(0)  {    fill_initialize(n, value);  }  explicit deque(size_type n)    : start(), finish(), map(0), map_size(0)  {    fill_initialize(n, value_type());  }#ifdef __STL_MEMBER_TEMPLATES  template <class InputIterator>  deque(InputIterator first, InputIterator last)    : start(), finish(), map(0), map_size(0)  {    range_initialize(first, last, iterator_category(first));  }#else /* __STL_MEMBER_TEMPLATES */  deque(const value_type* first, const value_type* last)    : start(), finish(), map(0), map_size(0)  {    create_map_and_nodes(last - first);    __STL_TRY {      uninitialized_copy(first, last, start);    }    __STL_UNWIND(destroy_map_and_nodes());  }  deque(const_iterator first, const_iterator last)    : start(), finish(), map(0), map_size(0)  {    create_map_and_nodes(last - first);    __STL_TRY {      uninitialized_copy(first, last, start);    }    __STL_UNWIND(destroy_map_and_nodes());  }#endif /* __STL_MEMBER_TEMPLATES */  ~deque()  {    destroy(start, finish);     // <stl_construct.h>    destroy_map_and_nodes();  }  deque& operator= (const deque& x)  {    // 其实我觉得把这个操作放在if内效率更高    const size_type len = size();    if (&x != this) {      // 当前容器比x容器拥有元素多, 析构多余元素      if (len >= x.size())        erase(copy(x.begin(), x.end(), start), finish);      // 将x所有超出部分的元素使用insert()追加进去      else {        const_iterator mid = x.begin() + difference_type(len);        copy(x.begin(), mid, start);        insert(finish, mid, x.end());      }    }    return *this;  }  // 其实要交换两个容器, 只需要交换其内部维护的指针即可^_^  void swap(deque& x)  {    __STD::swap(start, x.start);    __STD::swap(finish, x.finish);    __STD::swap(map, x.map);    __STD::swap(map_size, x.map_size);  }public:                         // push_* and pop_*  void push_back(const value_type& t)  {    // STL使用前闭后开的区间, 所以如果还有剩余容量,    // 则直接在finish.cur上构造对象即可, 然后更新迭代器    if (finish.cur != finish.last - 1) {      construct(finish.cur, t);      ++finish.cur;    }    // 容量已满就要新申请内存了    else      push_back_aux(t);  }  void push_front(const value_type& t)  {    if (start.cur != start.first) {      construct(start.cur - 1, t);      --start.cur;    }    else      push_front_aux(t);  }  void pop_back()  {    if (finish.cur != finish.first) {      --finish.cur;      destroy(finish.cur);    }    else      pop_back_aux();  }  void pop_front() {    if (start.cur != start.last - 1)    {      destroy(start.cur);      ++start.cur;    }    else      pop_front_aux();  }public:                         // Insert////////////////////////////////////////////////////////////////////////////////// 在指定位置前插入元素//////////////////////////////////////////////////////////////////////////////////             insert(iterator position, const value_type& x)//                                   |//                                   |---------------- 判断插入位置//                                   |//               -----------------------------------------------// deque.begin() |          deque.emd() |                      |//               |                      |                      |//               ↓                      ↓                      |//         push_front(x);         push_back(x);                |//                                                             ↓//                                                 insert_aux(position, x);//                                                 具体剖析见后面实现////////////////////////////////////////////////////////////////////////////////  iterator insert(iterator position, const value_type& x)  {    // 如果是在deque的最前端插入, 那么直接push_front()即可    if (position.cur == start.cur) {      push_front(x);      return start;    }    // 如果是在deque的末尾插入, 直接调用push_back()    else if (position.cur == finish.cur) {      push_back(x);      iterator tmp = finish;      --tmp;      return tmp;    }    else {      return insert_aux(position, x);    }  }  iterator insert(iterator position) { return insert(position, value_type()); }  // 详解见实现部分  void insert(iterator pos, size_type n, const value_type& x);  void insert(iterator pos, int n, const value_type& x)  {    insert(pos, (size_type) n, x);  }  void insert(iterator pos, long n, const value_type& x)  {    insert(pos, (size_type) n, x);  }#ifdef __STL_MEMBER_TEMPLATES  template <class InputIterator>  void insert(iterator pos, InputIterator first, InputIterator last)  {    insert(pos, first, last, iterator_category(first));  }#else /* __STL_MEMBER_TEMPLATES */  void insert(iterator pos, const value_type* first, const value_type* last);  void insert(iterator pos, const_iterator first, const_iterator last);#endif /* __STL_MEMBER_TEMPLATES */  // 如果new_size < size(), 那么就析构掉多余的元素,  // 否则以x为蓝本进行剩余元素的填充  void resize(size_type new_size, const value_type& x)  {    const size_type len = size();    if (new_size < len)      erase(start + new_size, finish);    else      insert(finish, new_size - len, x);  }  void resize(size_type new_size) { resize(new_size, value_type()); }public:                         // Erase  iterator erase(iterator pos)  {    iterator next = pos;    ++next;    // 计算待擦除点前的元素个数    difference_type index = pos - start;    // 判断待擦除结点前后元素的个数, 哪部分少就移动哪部分    if (index < (size() >> 1))    {      // 前面部分的元素少      copy_backward(start, pos, next);  // <stl_algobase.h>      pop_front();    }    // 后面部分的元素少    else {      copy(next, finish, pos);          // <stl_algobase.h>      pop_back();    }    return start + index;  }  // 详解见实现部分  iterator erase(iterator first, iterator last);  void clear();protected:                        // Internal construction/destruction  // 详解见实现部分  void create_map_and_nodes(size_type num_elements);  void destroy_map_and_nodes();  void fill_initialize(size_type n, const value_type& value);#ifdef __STL_MEMBER_TEMPLATES  template <class InputIterator>  void range_initialize(InputIterator first, InputIterator last,                        input_iterator_tag);  template <class ForwardIterator>  void range_initialize(ForwardIterator first, ForwardIterator last,                        forward_iterator_tag);#endif /* __STL_MEMBER_TEMPLATES */protected:                        // Internal push_* and pop_*  // 详解见实现部分  void push_back_aux(const value_type& t);  void push_front_aux(const value_type& t);  void pop_back_aux();  void pop_front_aux();protected:                        // Internal insert functions#ifdef __STL_MEMBER_TEMPLATES  template <class InputIterator>  void insert(iterator pos, InputIterator first, InputIterator last,              input_iterator_tag);  template <class ForwardIterator>  void insert(iterator pos, ForwardIterator first, ForwardIterator last,              forward_iterator_tag);#endif /* __STL_MEMBER_TEMPLATES */  iterator insert_aux(iterator pos, const value_type& x);  void insert_aux(iterator pos, size_type n, const value_type& x);#ifdef __STL_MEMBER_TEMPLATES  template <class ForwardIterator>  void insert_aux(iterator pos, ForwardIterator first, ForwardIterator last,                  size_type n);#else /* __STL_MEMBER_TEMPLATES */  void insert_aux(iterator pos,                  const value_type* first, const value_type* last,                  size_type n);  void insert_aux(iterator pos, const_iterator first, const_iterator last,                  size_type n);#endif /* __STL_MEMBER_TEMPLATES */  // 在起始缓冲区预留大小为n的空间  // 如果缓冲区不足则重新分配  iterator reserve_elements_at_front(size_type n)  {    size_type vacancies = start.cur - start.first;    if (n > vacancies)      new_elements_at_front(n - vacancies);    return start - difference_type(n);  }  iterator reserve_elements_at_back(size_type n)  {    size_type vacancies = (finish.last - finish.cur) - 1;    if (n > vacancies)      new_elements_at_back(n - vacancies);    return finish + difference_type(n);  }  void new_elements_at_front(size_type new_elements);  void new_elements_at_back(size_type new_elements);  void destroy_nodes_at_front(iterator before_start);  void destroy_nodes_at_back(iterator after_finish);protected:                      // Allocation of map and nodes  // Makes sure the map has space for new nodes.  Does not actually  //  add the nodes.  Can invalidate map pointers.  (And consequently,  //  deque iterators.)  void reserve_map_at_back (size_type nodes_to_add = 1)  {    if (nodes_to_add + 1 > map_size - (finish.node - map))      reallocate_map(nodes_to_add, false);  }  void reserve_map_at_front (size_type nodes_to_add = 1)  {    if (nodes_to_add > start.node - map)      reallocate_map(nodes_to_add, true);  }  void reallocate_map(size_type nodes_to_add, bool add_at_front);  // 分配内存, 不进行构造  pointer allocate_node() { return data_allocator::allocate(buffer_size()); }  // 释放内存, 不进行析构  void deallocate_node(pointer n)  {    data_allocator::deallocate(n, buffer_size());  }#ifdef __STL_NON_TYPE_TMPL_PARAM_BUGpublic:  bool operator==(const deque<T, Alloc, 0>& x) const {    return size() == x.size() && equal(begin(), end(), x.begin());  }  bool operator!=(const deque<T, Alloc, 0>& x) const {    return size() != x.size() || !equal(begin(), end(), x.begin());  }  bool operator<(const deque<T, Alloc, 0>& x) const {    return lexicographical_compare(begin(), end(), x.begin(), x.end());  }#endif /* __STL_NON_TYPE_TMPL_PARAM_BUG */};////////////////////////////////////////////////////////////////////////////////// 不进行内联的成员函数////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 在指定位置前插入n个值为x的元素//////////////////////////////////////////////////////////////////////////////////           insert(iterator pos, size_type n, const value_type& x)//                                   |//                                   |---------------- 判断插入位置//                                   |//               ---------------------------------------------------------// deque.begin() |                    deque.end() |                      |//               |                                |                      |//               ↓                                |                      |// reserve_elements_at_front(n);                  |                      |// uninitialized_fill(new_start, start, x);       |                      |//                                                ↓                      |//                          reserve_elements_at_back(n);                 |//                          uninitialized_fill(finish, new_finish, x);   |//                                                                       ↓//                                                       insert_aux(pos, n, x);//                                                       剖析见后面实现////////////////////////////////////////////////////////////////////////////////template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::insert(iterator pos,                                      size_type n, const value_type& x){  if (pos.cur == start.cur) {    iterator new_start = reserve_elements_at_front(n);    uninitialized_fill(new_start, start, x);    start = new_start;  }  else if (pos.cur == finish.cur) {    iterator new_finish = reserve_elements_at_back(n);    uninitialized_fill(finish, new_finish, x);    finish = new_finish;  }  else    insert_aux(pos, n, x);}// 给不支持成员函数模板的编译器提供支持函数#ifndef __STL_MEMBER_TEMPLATEStemplate <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::insert(iterator pos,                                      const value_type* first,                                      const value_type* last) {  size_type n = last - first;  if (pos.cur == start.cur) {    iterator new_start = reserve_elements_at_front(n);    __STL_TRY {      uninitialized_copy(first, last, new_start);      start = new_start;    }    __STL_UNWIND(destroy_nodes_at_front(new_start));  }  else if (pos.cur == finish.cur) {    iterator new_finish = reserve_elements_at_back(n);    __STL_TRY {      uninitialized_copy(first, last, finish);      finish = new_finish;    }    __STL_UNWIND(destroy_nodes_at_back(new_finish));  }  else    insert_aux(pos, first, last, n);}template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::insert(iterator pos,                                      const_iterator first,                                      const_iterator last){  size_type n = last - first;  if (pos.cur == start.cur) {    iterator new_start = reserve_elements_at_front(n);    __STL_TRY {      uninitialized_copy(first, last, new_start);      start = new_start;    }    __STL_UNWIND(destroy_nodes_at_front(new_start));  }  else if (pos.cur == finish.cur) {    iterator new_finish = reserve_elements_at_back(n);    __STL_TRY {      uninitialized_copy(first, last, finish);      finish = new_finish;    }    __STL_UNWIND(destroy_nodes_at_back(new_finish));  }  else    insert_aux(pos, first, last, n);}#endif /* __STL_MEMBER_TEMPLATES */////////////////////////////////////////////////////////////////////////////////// 擦除[first, last)区间的元素//////////////////////////////////////////////////////////////////////////////////                  erase(iterator first, iterator last)//                                   |//                                   |---------------- 是否要删除整个区间?//                                   |//               ------------------------------------------//           Yes |                                        | No//               |                                        |//               ↓                                        | --- 判断哪侧元素少//            clear();                                    ↓//       -----------------------------------------------------------------// 左侧少 |                                                         右侧少 |//       |                                                               |//       ↓                                                               ↓//   copy_backward(start, first, last);            copy(last, finish, first);//   new_start = start + n;                        new_finish = finish - n;//   析构多余的元素                                  析构多余的元素//   destroy(start, new_start);                    destroy(new_finish, finish);//   释放多余内存空间                                释放多余内存空间//   for (...)                                     for (...)//      ...                                             ...//   更新map状态                                    更新map状态////////////////////////////////////////////////////////////////////////////////template <class T, class Alloc, size_t BufSize>deque<T, Alloc, BufSize>::iteratordeque<T, Alloc, BufSize>::erase(iterator first, iterator last){  if (first == start && last == finish) {    clear();    return finish;  }  else {    difference_type n = last - first;    difference_type elems_before = first - start;    if (elems_before < (size() - n) / 2) {      copy_backward(start, first, last);      iterator new_start = start + n;      destroy(start, new_start);      for (map_pointer cur = start.node; cur < new_start.node; ++cur)        data_allocator::deallocate(*cur, buffer_size());      start = new_start;    }    else {      copy(last, finish, first);      iterator new_finish = finish - n;      destroy(new_finish, finish);      for (map_pointer cur = new_finish.node + 1; cur <= finish.node; ++cur)        data_allocator::deallocate(*cur, buffer_size());      finish = new_finish;    }    return start + elems_before;  }}template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::clear(){  // 首先析构除起点和终点的所有元素, 并释放相应空间  for (map_pointer node = start.node + 1; node < finish.node; ++node) {    destroy(*node, *node + buffer_size());    data_allocator::deallocate(*node, buffer_size());  }  // 如果deque本身不为空, 析构所有对象, 并释放掉结尾的内存  if (start.node != finish.node) {    destroy(start.cur, start.last);    destroy(finish.first, finish.cur);    data_allocator::deallocate(finish.first, buffer_size());  }  // 析构所有元素, 但是不释放空间, 因为deque要满足这个前置条件  // 具体的细节见本文件开头'特性'  else    destroy(start.cur, finish.cur);  finish = start;}// 创建内部使用的maptemplate <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::create_map_and_nodes(size_type num_elements){  // 需要的结点数, 元素个数 / 每个缓冲区能容纳的元素数 + 1  size_type num_nodes = num_elements / buffer_size() + 1;  // map要维护的结点, 这里最小的值为8, 见initial_map_size()  map_size = max(initial_map_size(), num_nodes + 2);  map = map_allocator::allocate(map_size);  // 将[nstart, nfinish)区间设置在map的中间,  // 这样就能保证前后增长而尽可能减少map的重新分配次数  map_pointer nstart = map + (map_size - num_nodes) / 2;  map_pointer nfinish = nstart + num_nodes - 1;  // 分配结点空间  map_pointer cur;  __STL_TRY {    for (cur = nstart; cur <= nfinish; ++cur)      *cur = allocate_node();  }#     ifdef  __STL_USE_EXCEPTIONS  catch(...) {    for (map_pointer n = nstart; n < cur; ++n)      deallocate_node(*n);    map_allocator::deallocate(map, map_size);    throw;  }#     endif /* __STL_USE_EXCEPTIONS */  // 维护指针状态  start.set_node(nstart);  finish.set_node(nfinish);  start.cur = start.first;  finish.cur = finish.first + num_elements % buffer_size();}// This is only used as a cleanup function in catch clauses.template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::destroy_map_and_nodes(){  for (map_pointer cur = start.node; cur <= finish.node; ++cur)    deallocate_node(*cur);  map_allocator::deallocate(map, map_size);}// 分配n个结点, 并以value为蓝本初始化template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::fill_initialize(size_type n,                                               const value_type& value){  create_map_and_nodes(n);  map_pointer cur;  __STL_TRY {    for (cur = start.node; cur < finish.node; ++cur)      uninitialized_fill(*cur, *cur + buffer_size(), value);    uninitialized_fill(finish.first, finish.cur, value);  }#       ifdef __STL_USE_EXCEPTIONS  catch(...) {    for (map_pointer n = start.node; n < cur; ++n)      destroy(*n, *n + buffer_size());    destroy_map_and_nodes();    throw;  }#       endif /* __STL_USE_EXCEPTIONS */}#ifdef __STL_MEMBER_TEMPLATEStemplate <class T, class Alloc, size_t BufSize>template <class InputIterator>void deque<T, Alloc, BufSize>::range_initialize(InputIterator first,                                                InputIterator last,                                                input_iterator_tag) {  create_map_and_nodes(0);  for ( ; first != last; ++first)    push_back(*first);}template <class T, class Alloc, size_t BufSize>template <class ForwardIterator>void deque<T, Alloc, BufSize>::range_initialize(ForwardIterator first,                                                ForwardIterator last,                                                forward_iterator_tag) {  size_type n = 0;  distance(first, last, n);  create_map_and_nodes(n);  __STL_TRY {    uninitialized_copy(first, last, start);  }  __STL_UNWIND(destroy_map_and_nodes());}#endif /* __STL_MEMBER_TEMPLATES */// 仅当finish.cur == finish.last - 1才调用// 即最后一个缓冲区没有空间才调用template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::push_back_aux(const value_type& t){  value_type t_copy = t;  reserve_map_at_back();  *(finish.node + 1) = allocate_node();  __STL_TRY {    construct(finish.cur, t_copy);    finish.set_node(finish.node + 1);    finish.cur = finish.first;  }  __STL_UNWIND(deallocate_node(*(finish.node + 1)));}// Called only if start.cur == start.first.template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::push_front_aux(const value_type& t){  value_type t_copy = t;  reserve_map_at_front();  *(start.node - 1) = allocate_node();  __STL_TRY {    start.set_node(start.node - 1);    start.cur = start.last - 1;    construct(start.cur, t_copy);  }#     ifdef __STL_USE_EXCEPTIONS  catch(...) {    start.set_node(start.node + 1);    start.cur = start.first;    deallocate_node(*(start.node - 1));    throw;  }#     endif /* __STL_USE_EXCEPTIONS */}// Called only if finish.cur == finish.first.template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>:: pop_back_aux(){  deallocate_node(finish.first);  finish.set_node(finish.node - 1);  finish.cur = finish.last - 1;  destroy(finish.cur);}// Called only if start.cur == start.last - 1.  Note that if the deque//  has at least one element (a necessary precondition for this member//  function), and if start.cur == start.last, then the deque must have//  at least two nodes.template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::pop_front_aux(){  destroy(start.cur);  deallocate_node(start.first);  start.set_node(start.node + 1);  start.cur = start.first;}#ifdef __STL_MEMBER_TEMPLATES// 将[first, last)区间元素插入到pos前template <class T, class Alloc, size_t BufSize>template <class InputIterator>void deque<T, Alloc, BufSize>::insert(iterator pos,                                      InputIterator first, InputIterator last,                                      input_iterator_tag){  // 由于是Input Iterator, 则使用通用的inserter完成插入操作  copy(first, last, inserter(*this, pos));}template <class T, class Alloc, size_t BufSize>template <class ForwardIterator>void deque<T, Alloc, BufSize>::insert(iterator pos,                                      ForwardIterator first,                                      ForwardIterator last,                                      forward_iterator_tag){  size_type n = 0;  distance(first, last, n);  if (pos.cur == start.cur) {    iterator new_start = reserve_elements_at_front(n);    __STL_TRY {      uninitialized_copy(first, last, new_start);      start = new_start;    }    __STL_UNWIND(destroy_nodes_at_front(new_start));  }  else if (pos.cur == finish.cur) {    iterator new_finish = reserve_elements_at_back(n);    __STL_TRY {      uninitialized_copy(first, last, finish);      finish = new_finish;    }    __STL_UNWIND(destroy_nodes_at_back(new_finish));  }  else    insert_aux(pos, first, last, n);}#endif /* __STL_MEMBER_TEMPLATES */////////////////////////////////////////////////////////////////////////////////// 在指定位置前插入元素//////////////////////////////////////////////////////////////////////////////////              insert_aux(iterator pos, const value_type& x)//                                   |//                                   |----------- 判断pos前端元素少还是后端元素少//                                   |//               -----------------------------------------------//         前端少 |                                       后端少 |//               |                                             |//               ↓                                             |//           进行相关操作                                   进行相关操作////////////////////////////////////////////////////////////////////////////////// 下面以pos前面元素少的情形进行说明, 为了简化, 假设操作不会超过一个缓冲区区间//// 插入前状态//           start            pos                                 end//             ↓               ↓                                   ↓// ---------------------------------------------------------------------// |   |   |   |   |   |   |   |   |   |   |   |   |   |   |   |   | X |// ---------------------------------------------------------------------//// 需要进行操作的区间//                需要拷贝的区间//                 -------------//       start     |           |                                  end//         ↓       ↓           ↓                                   ↓// ---------------------------------------------------------------------// |   |   |   |   |   |   |   |   |   |   |   |   |   |   |   |   | X |// ---------------------------------------------------------------------//             ↑   ↑       ↑   ↑//        front1   |       |   |//                 |       |   |//            front2       |   |//                         |   |//                       pos   |//                             |//                          pos1// 拷贝操作完成后////         这是[front2, pos1)//             ------------- --------- 这里是给待插入元素预留的空间//       start |           | |                                    end//         ↓   ↓           ↓ ↓                                     ↓// ---------------------------------------------------------------------// |   |   |   |   |   |   |   |   |   |   |   |   |   |   |   |   | X |// ---------------------------------------------------------------------//         ↑//   这里存储的是原来的front()//////////////////////////////////////////////////////////////////////////////////template <class T, class Alloc, size_t BufSize>typename deque<T, Alloc, BufSize>::iteratordeque<T, Alloc, BufSize>::insert_aux(iterator pos, const value_type& x){  difference_type index = pos - start;  value_type x_copy = x;  // 前面的时候用的移位操作, 这里怎么不用了呢^_^?  if (index < size() / 2) {    push_front(front());    iterator front1 = start;    ++front1;    iterator front2 = front1;    ++front2;    pos = start + index;    iterator pos1 = pos;    ++pos1;    copy(front2, pos1, front1);  }  else {    push_back(back());    iterator back1 = finish;    --back1;    iterator back2 = back1;    --back2;    pos = start + index;    copy_backward(pos, back2, back1);  }  *pos = x_copy;  return pos;}////////////////////////////////////////////////////////////////////////////////// 在pos前插入n个值为x的元素//////////////////////////////////////////////////////////////////////////////////         insert_aux(iterator pos, size_type n, const value_type& x)//                                   ↓//                      elems_before = pos - start;//                            length = size();//                                   |//                                   |---------- elems_before < length / 2 ?//                                   |           判断哪侧元素少, 就对哪侧进行操作//               ---------------------------------------//           Yes |                                     |  No//               |                                     |//               ↓                                     ↓// reserve_elements_at_front(n);          reserve_elements_at_back(n);// 根据具体情况进行元素的拷贝操作             根据具体情况进行元素的拷贝操作////////////////////////////////////////////////////////////////////////////////template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::insert_aux(iterator pos,                                          size_type n, const value_type& x){  const difference_type elems_before = pos - start;  size_type length = size();  value_type x_copy = x;  if (elems_before < length / 2) {    iterator new_start = reserve_elements_at_front(n);    iterator old_start = start;    pos = start + elems_before;    __STL_TRY {      if (elems_before >= difference_type(n)) {        iterator start_n = start + difference_type(n);        uninitialized_copy(start, start_n, new_start);        start = new_start;        copy(start_n, pos, old_start);        fill(pos - difference_type(n), pos, x_copy);      }      else {        __uninitialized_copy_fill(start, pos, new_start, start, x_copy);        start = new_start;        fill(old_start, pos, x_copy);      }    }    __STL_UNWIND(destroy_nodes_at_front(new_start));  }  else {    iterator new_finish = reserve_elements_at_back(n);    iterator old_finish = finish;    const difference_type elems_after = difference_type(length) - elems_before;    pos = finish - elems_after;    __STL_TRY {      if (elems_after > difference_type(n)) {        iterator finish_n = finish - difference_type(n);        uninitialized_copy(finish_n, finish, finish);        finish = new_finish;        copy_backward(pos, finish_n, old_finish);        fill(pos, pos + difference_type(n), x_copy);      }      else {        __uninitialized_fill_copy(finish, pos + difference_type(n),                                  x_copy,                                  pos, finish);        finish = new_finish;        fill(pos, old_finish, x_copy);      }    }    __STL_UNWIND(destroy_nodes_at_back(new_finish));  }}#ifdef __STL_MEMBER_TEMPLATES// 供给insert(iterator pos, ForwardIterator first, ForwardIterator last,)// 处理通用情况template <class T, class Alloc, size_t BufSize>template <class ForwardIterator>void deque<T, Alloc, BufSize>::insert_aux(iterator pos,                                          ForwardIterator first,                                          ForwardIterator last,                                          size_type n){  const difference_type elems_before = pos - start;  size_type length = size();  if (elems_before < length / 2) {    iterator new_start = reserve_elements_at_front(n);    iterator old_start = start;    pos = start + elems_before;    __STL_TRY {      if (elems_before >= difference_type(n)) {        iterator start_n = start + difference_type(n);        uninitialized_copy(start, start_n, new_start);        start = new_start;        copy(start_n, pos, old_start);        copy(first, last, pos - difference_type(n));      }      else {        ForwardIterator mid = first;        advance(mid, difference_type(n) - elems_before);        __uninitialized_copy_copy(start, pos, first, mid, new_start);        start = new_start;        copy(mid, last, old_start);      }    }    __STL_UNWIND(destroy_nodes_at_front(new_start));  }  else {    iterator new_finish = reserve_elements_at_back(n);    iterator old_finish = finish;    const difference_type elems_after = difference_type(length) - elems_before;    pos = finish - elems_after;    __STL_TRY {      if (elems_after > difference_type(n)) {        iterator finish_n = finish - difference_type(n);        uninitialized_copy(finish_n, finish, finish);        finish = new_finish;        copy_backward(pos, finish_n, old_finish);        copy(first, last, pos);      }      else {        ForwardIterator mid = first;        advance(mid, elems_after);        __uninitialized_copy_copy(mid, last, pos, finish, finish);        finish = new_finish;        copy(first, mid, pos);      }    }    __STL_UNWIND(destroy_nodes_at_back(new_finish));  }}#else /* __STL_MEMBER_TEMPLATES */template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::insert_aux(iterator pos,                                          const value_type* first,                                          const value_type* last,                                          size_type n){  const difference_type elems_before = pos - start;  size_type length = size();  if (elems_before < length / 2) {    iterator new_start = reserve_elements_at_front(n);    iterator old_start = start;    pos = start + elems_before;    __STL_TRY {      if (elems_before >= difference_type(n)) {        iterator start_n = start + difference_type(n);        uninitialized_copy(start, start_n, new_start);        start = new_start;        copy(start_n, pos, old_start);        copy(first, last, pos - difference_type(n));      }      else {        const value_type* mid = first + (difference_type(n) - elems_before);        __uninitialized_copy_copy(start, pos, first, mid, new_start);        start = new_start;        copy(mid, last, old_start);      }    }    __STL_UNWIND(destroy_nodes_at_front(new_start));  }  else {    iterator new_finish = reserve_elements_at_back(n);    iterator old_finish = finish;    const difference_type elems_after = difference_type(length) - elems_before;    pos = finish - elems_after;    __STL_TRY {      if (elems_after > difference_type(n)) {        iterator finish_n = finish - difference_type(n);        uninitialized_copy(finish_n, finish, finish);        finish = new_finish;        copy_backward(pos, finish_n, old_finish);        copy(first, last, pos);      }      else {        const value_type* mid = first + elems_after;        __uninitialized_copy_copy(mid, last, pos, finish, finish);        finish = new_finish;        copy(first, mid, pos);      }    }    __STL_UNWIND(destroy_nodes_at_back(new_finish));  }}template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::insert_aux(iterator pos,                                          const_iterator first,                                          const_iterator last,                                          size_type n){  const difference_type elems_before = pos - start;  size_type length = size();  if (elems_before < length / 2) {    iterator new_start = reserve_elements_at_front(n);    iterator old_start = start;    pos = start + elems_before;    __STL_TRY {      if (elems_before >= n) {        iterator start_n = start + n;        uninitialized_copy(start, start_n, new_start);        start = new_start;        copy(start_n, pos, old_start);        copy(first, last, pos - difference_type(n));      }      else {        const_iterator mid = first + (n - elems_before);        __uninitialized_copy_copy(start, pos, first, mid, new_start);        start = new_start;        copy(mid, last, old_start);      }    }    __STL_UNWIND(destroy_nodes_at_front(new_start));  }  else {    iterator new_finish = reserve_elements_at_back(n);    iterator old_finish = finish;    const difference_type elems_after = length - elems_before;    pos = finish - elems_after;    __STL_TRY {      if (elems_after > n) {        iterator finish_n = finish - difference_type(n);        uninitialized_copy(finish_n, finish, finish);        finish = new_finish;        copy_backward(pos, finish_n, old_finish);        copy(first, last, pos);      }      else {        const_iterator mid = first + elems_after;        __uninitialized_copy_copy(mid, last, pos, finish, finish);        finish = new_finish;        copy(first, mid, pos);      }    }    __STL_UNWIND(destroy_nodes_at_back(new_finish));  }}#endif /* __STL_MEMBER_TEMPLATES */// 在deque前端分配新结点template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::new_elements_at_front(size_type new_elements){  size_type new_nodes = (new_elements + buffer_size() - 1) / buffer_size();  reserve_map_at_front(new_nodes);  size_type i;  __STL_TRY {    for (i = 1; i <= new_nodes; ++i)      *(start.node - i) = allocate_node();  }#       ifdef __STL_USE_EXCEPTIONS  catch(...) {    for (size_type j = 1; j < i; ++j)      deallocate_node(*(start.node - j));    throw;  }#       endif /* __STL_USE_EXCEPTIONS */}// 在deque末尾分配新结点template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::new_elements_at_back(size_type new_elements) {  size_type new_nodes = (new_elements + buffer_size() - 1) / buffer_size();  reserve_map_at_back(new_nodes);  size_type i;  __STL_TRY {    for (i = 1; i <= new_nodes; ++i)      *(finish.node + i) = allocate_node();  }#       ifdef __STL_USE_EXCEPTIONS  catch(...) {    for (size_type j = 1; j < i; ++j)      deallocate_node(*(finish.node + j));    throw;  }#       endif /* __STL_USE_EXCEPTIONS */}// 释放[before_start.node, start.node)的结点template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::destroy_nodes_at_front(iterator before_start){  for (map_pointer n = before_start.node; n < start.node; ++n)    deallocate_node(*n);}// 释放(finish.node, after_finish.node]的结点template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::destroy_nodes_at_back(iterator after_finish){  for (map_pointer n = after_finish.node; n > finish.node; --n)    deallocate_node(*n);}// 重新配置map, 不会对缓冲区进行操作, map维护的是指向缓冲区的指针template <class T, class Alloc, size_t BufSize>void deque<T, Alloc, BufSize>::reallocate_map(size_type nodes_to_add,                                              bool add_at_front){  size_type old_num_nodes = finish.node - start.node + 1;  size_type new_num_nodes = old_num_nodes + nodes_to_add;  map_pointer new_nstart;  if (map_size > 2 * new_num_nodes) {    new_nstart = map + (map_size - new_num_nodes) / 2                     + (add_at_front ? nodes_to_add : 0);    if (new_nstart < start.node)      copy(start.node, finish.node + 1, new_nstart);    else      copy_backward(start.node, finish.node + 1, new_nstart + old_num_nodes);  }  else {    size_type new_map_size = map_size + max(map_size, nodes_to_add) + 2;    map_pointer new_map = map_allocator::allocate(new_map_size);    new_nstart = new_map + (new_map_size - new_num_nodes) / 2                         + (add_at_front ? nodes_to_add : 0);    copy(start.node, finish.node + 1, new_nstart);    map_allocator::deallocate(map, map_size);    map = new_map;    map_size = new_map_size;  }  start.set_node(new_nstart);  finish.set_node(new_nstart + old_num_nodes - 1);}// Nonmember functions.#ifndef __STL_NON_TYPE_TMPL_PARAM_BUGtemplate <class T, class Alloc, size_t BufSiz>bool operator==(const deque<T, Alloc, BufSiz>& x,                const deque<T, Alloc, BufSiz>& y) {  return x.size() == y.size() && equal(x.begin(), x.end(), y.begin());}template <class T, class Alloc, size_t BufSiz>bool operator<(const deque<T, Alloc, BufSiz>& x,               const deque<T, Alloc, BufSiz>& y) {  return lexicographical_compare(x.begin(), x.end(), y.begin(), y.end());}#endif /* __STL_NON_TYPE_TMPL_PARAM_BUG */#if defined(__STL_FUNCTION_TMPL_PARTIAL_ORDER) && \    !defined(__STL_NON_TYPE_TMPL_PARAM_BUG)template <class T, class Alloc, size_t BufSiz>inline void swap(deque<T, Alloc, BufSiz>& x, deque<T, Alloc, BufSiz>& y) {  x.swap(y);}#endif#if defined(__sgi) && !defined(__GNUC__) && (_MIPS_SIM != _MIPS_SIM_ABI32)#pragma reset woff 1174#endif__STL_END_NAMESPACE#endif /* __SGI_STL_INTERNAL_DEQUE_H */// Local Variables:// mode:C++// End:

原创粉丝点击