home *** CD-ROM | disk | FTP | other *** search
/ PC World 2000 January / PCWorld_2000-01_cd.bin / Software / Servis / Devc / _SETUP.4 / Group3 / stl_deque.h < prev    next >
C/C++ Source or Header  |  1998-03-08  |  42KB  |  1,336 lines

  1. /*
  2.  *
  3.  * Copyright (c) 1994
  4.  * Hewlett-Packard Company
  5.  *
  6.  * Permission to use, copy, modify, distribute and sell this software
  7.  * and its documentation for any purpose is hereby granted without fee,
  8.  * provided that the above copyright notice appear in all copies and
  9.  * that both that copyright notice and this permission notice appear
  10.  * in supporting documentation.  Hewlett-Packard Company makes no
  11.  * representations about the suitability of this software for any
  12.  * purpose.  It is provided "as is" without express or implied warranty.
  13.  *
  14.  *
  15.  * Copyright (c) 1997
  16.  * Silicon Graphics Computer Systems, Inc.
  17.  *
  18.  * Permission to use, copy, modify, distribute and sell this software
  19.  * and its documentation for any purpose is hereby granted without fee,
  20.  * provided that the above copyright notice appear in all copies and
  21.  * that both that copyright notice and this permission notice appear
  22.  * in supporting documentation.  Silicon Graphics makes no
  23.  * representations about the suitability of this software for any
  24.  * purpose.  It is provided "as is" without express or implied warranty.
  25.  */
  26.  
  27. /* NOTE: This is an internal header file, included by other STL headers.
  28.  *   You should not attempt to use it directly.
  29.  */
  30.  
  31. #ifndef __SGI_STL_INTERNAL_DEQUE_H
  32. #define __SGI_STL_INTERNAL_DEQUE_H
  33.  
  34. /* Class invariants:
  35.  *  For any nonsingular iterator i:
  36.  *    i.node is the address of an element in the map array.  The
  37.  *      contents of i.node is a pointer to the beginning of a node.
  38.  *    i.first == *(i.node) 
  39.  *    i.last  == i.first + node_size
  40.  *    i.cur is a pointer in the range [i.first, i.last).  NOTE:
  41.  *      the implication of this is that i.cur is always a dereferenceable
  42.  *      pointer, even if i is a past-the-end iterator.
  43.  *  Start and Finish are always nonsingular iterators.  NOTE: this means
  44.  *    that an empty deque must have one node, and that a deque
  45.  *    with N elements, where N is the buffer size, must have two nodes.
  46.  *  For every node other than start.node and finish.node, every element
  47.  *    in the node is an initialized object.  If start.node == finish.node,
  48.  *    then [start.cur, finish.cur) are initialized objects, and
  49.  *    the elements outside that range are uninitialized storage.  Otherwise,
  50.  *    [start.cur, start.last) and [finish.first, finish.cur) are initialized
  51.  *    objects, and [start.first, start.cur) and [finish.cur, finish.last)
  52.  *    are uninitialized storage.
  53.  *  [map, map + map_size) is a valid, non-empty range.  
  54.  *  [start.node, finish.node] is a valid range contained within 
  55.  *    [map, map + map_size).  
  56.  *  A pointer in the range [map, map + map_size) points to an allocated
  57.  *    node if and only if the pointer is in the range [start.node, finish.node].
  58.  */
  59.  
  60.  
  61. /*
  62.  * In previous versions of deque, node_size was fixed by the 
  63.  * implementation.  In this version, however, users can select
  64.  * the node size.  Deque has three template parameters; the third,
  65.  * a number of type size_t, is the number of elements per node.
  66.  * If the third template parameter is 0 (which is the default), 
  67.  * then deque will use a default node size.
  68.  *
  69.  * The only reason for using an alternate node size is if your application
  70.  * requires a different performance tradeoff than the default.  If,
  71.  * for example, your program contains many deques each of which contains
  72.  * only a few elements, then you might want to save memory (possibly
  73.  * by sacrificing some speed) by using smaller nodes.
  74.  *
  75.  * Unfortunately, some compilers have trouble with non-type template 
  76.  * parameters; stl_config.h defines __STL_NON_TYPE_TMPL_PARAM_BUG if
  77.  * that is the case.  If your compiler is one of them, then you will
  78.  * not be able to use alternate node sizes; you will have to use the
  79.  * default value.
  80.  */
  81.  
  82. __STL_BEGIN_NAMESPACE 
  83.  
  84. #if defined(__sgi) && !defined(__GNUC__) && (_MIPS_SIM != _MIPS_SIM_ABI32)
  85. #pragma set woff 1174
  86. #endif
  87.  
  88. // Note: this function is simply a kludge to work around several compilers'
  89. //  bugs in handling constant expressions.
  90. inline size_t __deque_buf_size(size_t n, size_t sz)
  91. {
  92.   return n != 0 ? n : (sz < 512 ? size_t(512 / sz) : size_t(1));
  93. }
  94.  
  95. #ifndef __STL_NON_TYPE_TMPL_PARAM_BUG
  96. template <class T, class Ref, class Ptr, size_t BufSiz>
  97. struct __deque_iterator {
  98.   typedef __deque_iterator<T, T&, T*, BufSiz>             iterator;
  99.   typedef __deque_iterator<T, const T&, const T*, BufSiz> const_iterator;
  100.   static size_t buffer_size() {return __deque_buf_size(BufSiz, sizeof(T)); }
  101. #else /* __STL_NON_TYPE_TMPL_PARAM_BUG */
  102. template <class T, class Ref, class Ptr>
  103. struct __deque_iterator {
  104.   typedef __deque_iterator<T, T&, T*>             iterator;
  105.   typedef __deque_iterator<T, const T&, const T*> const_iterator;
  106.   static size_t buffer_size() {return __deque_buf_size(0, sizeof(T)); }
  107. #endif
  108.  
  109.   typedef random_access_iterator_tag iterator_category;
  110.   typedef T value_type;
  111.   typedef Ptr pointer;
  112.   typedef Ref reference;
  113.   typedef size_t size_type;
  114.   typedef ptrdiff_t difference_type;
  115.   typedef T** map_pointer;
  116.  
  117.   typedef __deque_iterator self;
  118.  
  119.   T* cur;
  120.   T* first;
  121.   T* last;
  122.   map_pointer node;
  123.  
  124.   __deque_iterator(T* x, map_pointer y) 
  125.     : cur(x), first(*y), last(*y + buffer_size()), node(y) {}
  126.   __deque_iterator() : cur(0), first(0), last(0), node(0) {}
  127.   __deque_iterator(const iterator& x)
  128.     : cur(x.cur), first(x.first), last(x.last), node(x.node) {}
  129.  
  130.   reference operator*() const { return *cur; }
  131. #ifndef __SGI_STL_NO_ARROW_OPERATOR
  132.   pointer operator->() const { return &(operator*()); }
  133. #endif /* __SGI_STL_NO_ARROW_OPERATOR */
  134.  
  135.   difference_type operator-(const self& x) const {
  136.     return difference_type(buffer_size()) * (node - x.node - 1) +
  137.       (cur - first) + (x.last - x.cur);
  138.   }
  139.  
  140.   self& operator++() {
  141.     ++cur;
  142.     if (cur == last) {
  143.       set_node(node + 1);
  144.       cur = first;
  145.     }
  146.     return *this; 
  147.   }
  148.   self operator++(int)  {
  149.     self tmp = *this;
  150.     ++*this;
  151.     return tmp;
  152.   }
  153.  
  154.   self& operator--() {
  155.     if (cur == first) {
  156.       set_node(node - 1);
  157.       cur = last;
  158.     }
  159.     --cur;
  160.     return *this;
  161.   }
  162.   self operator--(int) {
  163.     self tmp = *this;
  164.     --*this;
  165.     return tmp;
  166.   }
  167.  
  168.   self& operator+=(difference_type n) {
  169.     difference_type offset = n + (cur - first);
  170.     if (offset >= 0 && offset < difference_type(buffer_size()))
  171.       cur += n;
  172.     else {
  173.       difference_type node_offset =
  174.         offset > 0 ? offset / difference_type(buffer_size())
  175.                    : -difference_type((-offset - 1) / buffer_size()) - 1;
  176.       set_node(node + node_offset);
  177.       cur = first + (offset - node_offset * difference_type(buffer_size()));
  178.     }
  179.     return *this;
  180.   }
  181.  
  182.   self operator+(difference_type n) const {
  183.     self tmp = *this;
  184.     return tmp += n;
  185.   }
  186.  
  187.   self& operator-=(difference_type n) { return *this += -n; }
  188.  
  189.   self operator-(difference_type n) const {
  190.     self tmp = *this;
  191.     return tmp -= n;
  192.   }
  193.  
  194.   reference operator[](difference_type n) const { return *(*this + n); }
  195.  
  196.   bool operator==(const self& x) const { return cur == x.cur; }
  197.   bool operator!=(const self& x) const { return !(*this == x); }
  198.   bool operator<(const self& x) const {
  199.     return (node == x.node) ? (cur < x.cur) : (node < x.node);
  200.   }
  201.  
  202.   void set_node(map_pointer new_node) {
  203.     node = new_node;
  204.     first = *new_node;
  205.     last = first + difference_type(buffer_size());
  206.   }
  207. };
  208.  
  209. #ifndef __STL_CLASS_PARTIAL_SPECIALIZATION
  210.  
  211. #ifndef __STL_NON_TYPE_TMPL_PARAM_BUG
  212.  
  213. template <class T, class Ref, class Ptr, size_t BufSiz>
  214. inline random_access_iterator_tag
  215. iterator_category(const __deque_iterator<T, Ref, Ptr, BufSiz>&) {
  216.   return random_access_iterator_tag();
  217. }
  218.  
  219. template <class T, class Ref, class Ptr, size_t BufSiz>
  220. inline T* value_type(const __deque_iterator<T, Ref, Ptr, BufSiz>&) {
  221.   return 0;
  222. }
  223.  
  224. template <class T, class Ref, class Ptr, size_t BufSiz>
  225. inline ptrdiff_t* distance_type(const __deque_iterator<T, Ref, Ptr, BufSiz>&) {
  226.   return 0;
  227. }
  228.  
  229. #else /* __STL_NON_TYPE_TMPL_PARAM_BUG */
  230.  
  231. template <class T, class Ref, class Ptr>
  232. inline random_access_iterator_tag
  233. iterator_category(const __deque_iterator<T, Ref, Ptr>&) {
  234.   return random_access_iterator_tag();
  235. }
  236.  
  237. template <class T, class Ref, class Ptr>
  238. inline T* value_type(const __deque_iterator<T, Ref, Ptr>&) { return 0; }
  239.  
  240. template <class T, class Ref, class Ptr>
  241. inline ptrdiff_t* distance_type(const __deque_iterator<T, Ref, Ptr>&) {
  242.   return 0;
  243. }
  244.  
  245. #endif /* __STL_NON_TYPE_TMPL_PARAM_BUG */
  246.  
  247. #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */
  248.  
  249. // See __deque_buf_size().  The only reason that the default value is 0
  250. //  is as a workaround for bugs in the way that some compilers handle
  251. //  constant expressions.
  252. template <class T, class Alloc = alloc, size_t BufSiz = 0> 
  253. class deque {
  254. public:                         // Basic types
  255.   typedef T value_type;
  256.   typedef value_type* pointer;
  257.   typedef const value_type* const_pointer;
  258.   typedef value_type& reference;
  259.   typedef const value_type& const_reference;
  260.   typedef size_t size_type;
  261.   typedef ptrdiff_t difference_type;
  262.  
  263. public:                         // Iterators
  264. #ifndef __STL_NON_TYPE_TMPL_PARAM_BUG
  265.   typedef __deque_iterator<T, T&, T*, BufSiz>              iterator;
  266.   typedef __deque_iterator<T, const T&, const T&, BufSiz>  const_iterator;
  267. #else /* __STL_NON_TYPE_TMPL_PARAM_BUG */
  268.   typedef __deque_iterator<T, T&, T*>                      iterator;
  269.   typedef __deque_iterator<T, const T&, const T*>          const_iterator;
  270. #endif /* __STL_NON_TYPE_TMPL_PARAM_BUG */
  271.  
  272. #ifdef __STL_CLASS_PARTIAL_SPECIALIZATION
  273.   typedef reverse_iterator<const_iterator> const_reverse_iterator;
  274.   typedef reverse_iterator<iterator> reverse_iterator;
  275. #else /* __STL_CLASS_PARTIAL_SPECIALIZATION */
  276.   typedef reverse_iterator<const_iterator, value_type, const_reference, 
  277.                            difference_type>  
  278.           const_reverse_iterator;
  279.   typedef reverse_iterator<iterator, value_type, reference, difference_type>
  280.           reverse_iterator; 
  281. #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */
  282.  
  283. protected:                      // Internal typedefs
  284.   typedef pointer* map_pointer;
  285.   typedef simple_alloc<value_type, Alloc> data_allocator;
  286.   typedef simple_alloc<pointer, Alloc> map_allocator;
  287.  
  288.   static size_type buffer_size() {
  289.     return __deque_buf_size(BufSiz, sizeof(value_type));
  290.   }
  291.   static size_type initial_map_size() { return 8; }
  292.  
  293. protected:                      // Data members
  294.   iterator start;
  295.   iterator finish;
  296.  
  297.   map_pointer map;
  298.   size_type map_size;
  299.  
  300. public:                         // Basic accessors
  301.   iterator begin() { return start; }
  302.   iterator end() { return finish; }
  303.   const_iterator begin() const { return start; }
  304.   const_iterator end() const { return finish; }
  305.  
  306.   reverse_iterator rbegin() { return reverse_iterator(finish); }
  307.   reverse_iterator rend() { return reverse_iterator(start); }
  308.   const_reverse_iterator rbegin() const {
  309.     return const_reverse_iterator(finish);
  310.   }
  311.   const_reverse_iterator rend() const {
  312.     return const_reverse_iterator(start);
  313.   }
  314.  
  315.   reference operator[](size_type n) { return start[difference_type(n)]; }
  316.   const_reference operator[](size_type n) const {
  317.     return start[difference_type(n)];
  318.   }
  319.  
  320.   reference front() { return *start; }
  321.   reference back() {
  322.     iterator tmp = finish;
  323.     --tmp;
  324.     return *tmp;
  325.   }
  326.   const_reference front() const { return *start; }
  327.   const_reference back() const {
  328.     const_iterator tmp = finish;
  329.     --tmp;
  330.     return *tmp;
  331.   }
  332.  
  333.   size_type size() const { return finish - start;; }
  334.   size_type max_size() const { return size_type(-1); }
  335.   bool empty() const { return finish == start; }
  336.  
  337. public:                         // Constructor, destructor.
  338.   deque()
  339.     : start(), finish(), map(0), map_size(0)
  340.   {
  341.     create_map_and_nodes(0);
  342.   }
  343.  
  344.   deque(const deque& x)
  345.     : start(), finish(), map(0), map_size(0)
  346.   {
  347.     create_map_and_nodes(x.size());
  348.     __STL_TRY {
  349.       uninitialized_copy(x.begin(), x.end(), start);
  350.     }
  351.     __STL_UNWIND(destroy_map_and_nodes());
  352.   }
  353.  
  354.   deque(size_type n, const value_type& value)
  355.     : start(), finish(), map(0), map_size(0)
  356.   {
  357.     fill_initialize(n, value);
  358.   }
  359.  
  360.   deque(int n, const value_type& value)
  361.     : start(), finish(), map(0), map_size(0)
  362.   {
  363.     fill_initialize(n, value);
  364.   }
  365.  
  366.   deque(long n, const value_type& value)
  367.     : start(), finish(), map(0), map_size(0)
  368.   {
  369.     fill_initialize(n, value);
  370.   }
  371.  
  372.   explicit deque(size_type n)
  373.     : start(), finish(), map(0), map_size(0)
  374.   {
  375.     fill_initialize(n, value_type());
  376.   }
  377.  
  378. #ifdef __STL_MEMBER_TEMPLATES
  379.  
  380.   template <class InputIterator>
  381.   deque(InputIterator first, InputIterator last)
  382.     : start(), finish(), map(0), map_size(0)
  383.   {
  384.     range_initialize(first, last, iterator_category(first));
  385.   }
  386.  
  387. #else /* __STL_MEMBER_TEMPLATES */
  388.  
  389.   deque(const value_type* first, const value_type* last)
  390.     : start(), finish(), map(0), map_size(0)
  391.   {
  392.     create_map_and_nodes(last - first);
  393.     __STL_TRY {
  394.       uninitialized_copy(first, last, start);
  395.     }
  396.     __STL_UNWIND(destroy_map_and_nodes());
  397.   }
  398.  
  399.   deque(const_iterator first, const_iterator last)
  400.     : start(), finish(), map(0), map_size(0)
  401.   {
  402.     create_map_and_nodes(last - first);
  403.     __STL_TRY {
  404.       uninitialized_copy(first, last, start);
  405.     }
  406.     __STL_UNWIND(destroy_map_and_nodes());
  407.   }
  408.  
  409. #endif /* __STL_MEMBER_TEMPLATES */
  410.  
  411.   ~deque() {
  412.     destroy(start, finish);
  413.     destroy_map_and_nodes();
  414.   }
  415.  
  416.   deque& operator= (const deque& x) {
  417.     const size_type len = size();
  418.     if (&x != this) {
  419.       if (len >= x.size())
  420.         erase(copy(x.begin(), x.end(), start), finish);
  421.       else {
  422.         const_iterator mid = x.begin() + difference_type(len);
  423.         copy(x.begin(), mid, start);
  424.         insert(finish, mid, x.end());
  425.       }
  426.     }
  427.     return *this;
  428.   }        
  429.  
  430.   void swap(deque& x) {
  431.     __STD::swap(start, x.start);
  432.     __STD::swap(finish, x.finish);
  433.     __STD::swap(map, x.map);
  434.     __STD::swap(map_size, x.map_size);
  435.   }
  436.  
  437. public:                         // push_* and pop_*
  438.   
  439.   void push_back(const value_type& t) {
  440.     if (finish.cur != finish.last - 1) {
  441.       construct(finish.cur, t);
  442.       ++finish.cur;
  443.     }
  444.     else
  445.       push_back_aux(t);
  446.   }
  447.  
  448.   void push_front(const value_type& t) {
  449.     if (start.cur != start.first) {
  450.       construct(start.cur - 1, t);
  451.       --start.cur;
  452.     }
  453.     else
  454.       push_front_aux(t);
  455.   }
  456.  
  457.   void pop_back() {
  458.     if (finish.cur != finish.first) {
  459.       --finish.cur;
  460.       destroy(finish.cur);
  461.     }
  462.     else
  463.       pop_back_aux();
  464.   }
  465.  
  466.   void pop_front() {
  467.     if (start.cur != start.last - 1) {
  468.       destroy(start.cur);
  469.       ++start.cur;
  470.     }
  471.     else 
  472.       pop_front_aux();
  473.   }
  474.  
  475. public:                         // Insert
  476.  
  477.   iterator insert(iterator position, const value_type& x) {
  478.     if (position.cur == start.cur) {
  479.       push_front(x);
  480.       return start;
  481.     }
  482.     else if (position.cur == finish.cur) {
  483.       push_back(x);
  484.       iterator tmp = finish;
  485.       --tmp;
  486.       return tmp;
  487.     }
  488.     else {
  489.       return insert_aux(position, x);
  490.     }
  491.   }
  492.  
  493.   iterator insert(iterator position) { return insert(position, value_type()); }
  494.  
  495.   void insert(iterator pos, size_type n, const value_type& x); 
  496.  
  497.   void insert(iterator pos, int n, const value_type& x) {
  498.     insert(pos, (size_type) n, x);
  499.   }
  500.   void insert(iterator pos, long n, const value_type& x) {
  501.     insert(pos, (size_type) n, x);
  502.   }
  503.  
  504. #ifdef __STL_MEMBER_TEMPLATES  
  505.  
  506.   template <class InputIterator>
  507.   void insert(iterator pos, InputIterator first, InputIterator last) {
  508.     insert(pos, first, last, iterator_category(first));
  509.   }
  510.  
  511. #else /* __STL_MEMBER_TEMPLATES */
  512.  
  513.   void insert(iterator pos, const value_type* first, const value_type* last);
  514.   void insert(iterator pos, const_iterator first, const_iterator last);
  515.  
  516. #endif /* __STL_MEMBER_TEMPLATES */
  517.  
  518.   void resize(size_type new_size, const value_type& x) {
  519.     const size_type len = size();
  520.     if (new_size < len) 
  521.       erase(start + new_size, finish);
  522.     else
  523.       insert(finish, new_size - len, x);
  524.   }
  525.  
  526.   void resize(size_type new_size) { resize(new_size, value_type()); }
  527.  
  528. public:                         // Erase
  529.   iterator erase(iterator pos) {
  530.     iterator next = pos;
  531.     ++next;
  532.     difference_type index = pos - start;
  533.     if (index < (size() >> 1)) {
  534.       copy_backward(start, pos, next);
  535.       pop_front();
  536.     }
  537.     else {
  538.       copy(next, finish, pos);
  539.       pop_back();
  540.     }
  541.     return start + index;
  542.   }
  543.  
  544.   iterator erase(iterator first, iterator last);
  545.   void clear(); 
  546.  
  547. protected:                        // Internal construction/destruction
  548.  
  549.   void create_map_and_nodes(size_type num_elements);
  550.   void destroy_map_and_nodes();
  551.   void fill_initialize(size_type n, const value_type& value);
  552.  
  553. #ifdef __STL_MEMBER_TEMPLATES  
  554.  
  555.   template <class InputIterator>
  556.   void range_initialize(InputIterator first, InputIterator last,
  557.                         input_iterator_tag);
  558.  
  559.   template <class ForwardIterator>
  560.   void range_initialize(ForwardIterator first, ForwardIterator last,
  561.                         forward_iterator_tag);
  562.  
  563. #endif /* __STL_MEMBER_TEMPLATES */
  564.  
  565. protected:                        // Internal push_* and pop_*
  566.  
  567.   void push_back_aux(const value_type& t);
  568.   void push_front_aux(const value_type& t);
  569.   void pop_back_aux();
  570.   void pop_front_aux();
  571.  
  572. protected:                        // Internal insert functions
  573.  
  574. #ifdef __STL_MEMBER_TEMPLATES  
  575.  
  576.   template <class InputIterator>
  577.   void insert(iterator pos, InputIterator first, InputIterator last,
  578.               input_iterator_tag);
  579.  
  580.   template <class ForwardIterator>
  581.   void insert(iterator pos, ForwardIterator first, ForwardIterator last,
  582.               forward_iterator_tag);
  583.  
  584. #endif /* __STL_MEMBER_TEMPLATES */
  585.  
  586.   iterator insert_aux(iterator pos, const value_type& x);
  587.   void insert_aux(iterator pos, size_type n, const value_type& x);
  588.  
  589. #ifdef __STL_MEMBER_TEMPLATES  
  590.  
  591.   template <class ForwardIterator>
  592.   void insert_aux(iterator pos, ForwardIterator first, ForwardIterator last,
  593.                   size_type n);
  594.  
  595. #else /* __STL_MEMBER_TEMPLATES */
  596.   
  597.   void insert_aux(iterator pos,
  598.                   const value_type* first, const value_type* last,
  599.                   size_type n);
  600.  
  601.   void insert_aux(iterator pos, const_iterator first, const_iterator last,
  602.                   size_type n);
  603.  
  604. #endif /* __STL_MEMBER_TEMPLATES */
  605.  
  606.   iterator reserve_elements_at_front(size_type n) {
  607.     size_type vacancies = start.cur - start.first;
  608.     if (n > vacancies) 
  609.       new_elements_at_front(n - vacancies);
  610.     return start - difference_type(n);
  611.   }
  612.  
  613.   iterator reserve_elements_at_back(size_type n) {
  614.     size_type vacancies = (finish.last - finish.cur) - 1;
  615.     if (n > vacancies)
  616.       new_elements_at_back(n - vacancies);
  617.     return finish + difference_type(n);
  618.   }
  619.  
  620.   void new_elements_at_front(size_type new_elements);
  621.   void new_elements_at_back(size_type new_elements);
  622.  
  623.   void destroy_nodes_at_front(iterator before_start);
  624.   void destroy_nodes_at_back(iterator after_finish);
  625.  
  626. protected:                      // Allocation of map and nodes
  627.  
  628.   // Makes sure the map has space for new nodes.  Does not actually
  629.   //  add the nodes.  Can invalidate map pointers.  (And consequently, 
  630.   //  deque iterators.)
  631.  
  632.   void reserve_map_at_back (size_type nodes_to_add = 1) {
  633.     if (nodes_to_add + 1 > map_size - (finish.node - map))
  634.       reallocate_map(nodes_to_add, false);
  635.   }
  636.  
  637.   void reserve_map_at_front (size_type nodes_to_add = 1) {
  638.     if (nodes_to_add > start.node - map)
  639.       reallocate_map(nodes_to_add, true);
  640.   }
  641.  
  642.   void reallocate_map(size_type nodes_to_add, bool add_at_front);
  643.  
  644.   pointer allocate_node() { return data_allocator::allocate(buffer_size()); }
  645.   void deallocate_node(pointer n) {
  646.     data_allocator::deallocate(n, buffer_size());
  647.   }
  648.  
  649. #ifdef __STL_NON_TYPE_TMPL_PARAM_BUG
  650. public:
  651.   bool operator==(const deque<T, Alloc, 0>& x) const {
  652.     return size() == x.size() && equal(begin(), end(), x.begin());
  653.   }
  654.   bool operator!=(const deque<T, Alloc, 0>& x) const {
  655.     return size() != x.size() || !equal(begin(), end(), x.begin());
  656.   }
  657.   bool operator<(const deque<T, Alloc, 0>& x) const {
  658.     return lexicographical_compare(begin(), end(), x.begin(), x.end());
  659.   }
  660. #endif /* __STL_NON_TYPE_TMPL_PARAM_BUG */
  661. };
  662.  
  663. // Non-inline member functions
  664.  
  665. template <class T, class Alloc, size_t BufSize>
  666. void deque<T, Alloc, BufSize>::insert(iterator pos,
  667.                                       size_type n, const value_type& x) {
  668.   if (pos.cur == start.cur) {
  669.     iterator new_start = reserve_elements_at_front(n);
  670.     uninitialized_fill(new_start, start, x);
  671.     start = new_start;
  672.   }
  673.   else if (pos.cur == finish.cur) {
  674.     iterator new_finish = reserve_elements_at_back(n);
  675.     uninitialized_fill(finish, new_finish, x);
  676.     finish = new_finish;
  677.   }
  678.   else 
  679.     insert_aux(pos, n, x);
  680. }
  681.  
  682. #ifndef __STL_MEMBER_TEMPLATES  
  683.  
  684. template <class T, class Alloc, size_t BufSize>
  685. void deque<T, Alloc, BufSize>::insert(iterator pos,
  686.                                       const value_type* first,
  687.                                       const value_type* last) {
  688.   size_type n = last - first;
  689.   if (pos.cur == start.cur) {
  690.     iterator new_start = reserve_elements_at_front(n);
  691.     __STL_TRY {
  692.       uninitialized_copy(first, last, new_start);
  693.       start = new_start;
  694.     }
  695.     __STL_UNWIND(destroy_nodes_at_front(new_start));
  696.   }
  697.   else if (pos.cur == finish.cur) {
  698.     iterator new_finish = reserve_elements_at_back(n);
  699.     __STL_TRY {
  700.       uninitialized_copy(first, last, finish);
  701.       finish = new_finish;
  702.     }
  703.     __STL_UNWIND(destroy_nodes_at_back(new_finish));
  704.   }
  705.   else
  706.     insert_aux(pos, first, last, n);
  707. }
  708.  
  709. template <class T, class Alloc, size_t BufSize>
  710. void deque<T, Alloc, BufSize>::insert(iterator pos,
  711.                                       const_iterator first,
  712.                                       const_iterator last)
  713. {
  714.   size_type n = last - first;
  715.   if (pos.cur == start.cur) {
  716.     iterator new_start = reserve_elements_at_front(n);
  717.     __STL_TRY {
  718.       uninitialized_copy(first, last, new_start);
  719.       start = new_start;
  720.     }
  721.     __STL_UNWIND(destroy_nodes_at_front(new_start));
  722.   }
  723.   else if (pos.cur == finish.cur) {
  724.     iterator new_finish = reserve_elements_at_back(n);
  725.     __STL_TRY {
  726.       uninitialized_copy(first, last, finish);
  727.       finish = new_finish;
  728.     }
  729.     __STL_UNWIND(destroy_nodes_at_back(new_finish));
  730.   }
  731.   else
  732.     insert_aux(pos, first, last, n);
  733. }
  734.  
  735. #endif /* __STL_MEMBER_TEMPLATES */
  736.  
  737. template <class T, class Alloc, size_t BufSize>
  738. deque<T, Alloc, BufSize>::iterator 
  739. deque<T, Alloc, BufSize>::erase(iterator first, iterator last) {
  740.   if (first == start && last == finish) {
  741.     clear();
  742.     return finish;
  743.   }
  744.   else {
  745.     difference_type n = last - first;
  746.     difference_type elems_before = first - start;
  747.     if (elems_before < (size() - n) / 2) {
  748.       copy_backward(start, first, last);
  749.       iterator new_start = start + n;
  750.       destroy(start, new_start);
  751.       for (map_pointer cur = start.node; cur < new_start.node; ++cur)
  752.         data_allocator::deallocate(*cur, buffer_size());
  753.       start = new_start;
  754.     }
  755.     else {
  756.       copy(last, finish, first);
  757.       iterator new_finish = finish - n;
  758.       destroy(new_finish, finish);
  759.       for (map_pointer cur = new_finish.node + 1; cur <= finish.node; ++cur)
  760.         data_allocator::deallocate(*cur, buffer_size());
  761.       finish = new_finish;
  762.     }
  763.     return start + elems_before;
  764.   }
  765. }
  766.  
  767. template <class T, class Alloc, size_t BufSize>
  768. void deque<T, Alloc, BufSize>::clear() {
  769.   for (map_pointer node = start.node + 1; node < finish.node; ++node) {
  770.     destroy(*node, *node + buffer_size());
  771.     data_allocator::deallocate(*node, buffer_size());
  772.   }
  773.  
  774.   if (start.node != finish.node) {
  775.     destroy(start.cur, start.last);
  776.     destroy(finish.first, finish.cur);
  777.     data_allocator::deallocate(finish.first, buffer_size());
  778.   }
  779.   else
  780.     destroy(start.cur, finish.cur);
  781.  
  782.   finish = start;
  783. }
  784.  
  785. template <class T, class Alloc, size_t BufSize>
  786. void deque<T, Alloc, BufSize>::create_map_and_nodes(size_type num_elements) {
  787.   size_type num_nodes = num_elements / buffer_size() + 1;
  788.  
  789.   map_size = max(initial_map_size(), num_nodes + 2);
  790.   map = map_allocator::allocate(map_size);
  791.  
  792.   map_pointer nstart = map + (map_size - num_nodes) / 2;
  793.   map_pointer nfinish = nstart + num_nodes - 1;
  794.     
  795.   map_pointer cur;
  796.   __STL_TRY {
  797.     for (cur = nstart; cur <= nfinish; ++cur)
  798.       *cur = allocate_node();
  799.   }
  800. #     ifdef  __STL_USE_EXCEPTIONS 
  801.   catch(...) {
  802.     for (map_pointer n = nstart; n < cur; ++n)
  803.       deallocate_node(*n);
  804.     map_allocator::deallocate(map, map_size);
  805.     throw;
  806.   }
  807. #     endif /* __STL_USE_EXCEPTIONS */
  808.  
  809.   start.set_node(nstart);
  810.   finish.set_node(nfinish);
  811.   start.cur = start.first;
  812.   finish.cur = finish.first + num_elements % buffer_size();
  813. }
  814.  
  815. // This is only used as a cleanup function in catch clauses.
  816. template <class T, class Alloc, size_t BufSize>
  817. void deque<T, Alloc, BufSize>::destroy_map_and_nodes() {
  818.   for (map_pointer cur = start.node; cur <= finish.node; ++cur)
  819.     deallocate_node(*cur);
  820.   map_allocator::deallocate(map, map_size);
  821. }
  822.   
  823.  
  824. template <class T, class Alloc, size_t BufSize>
  825. void deque<T, Alloc, BufSize>::fill_initialize(size_type n,
  826.                                                const value_type& value) {
  827.   create_map_and_nodes(n);
  828.   map_pointer cur;
  829.   __STL_TRY {
  830.     for (cur = start.node; cur < finish.node; ++cur)
  831.       uninitialized_fill(*cur, *cur + buffer_size(), value);
  832.     uninitialized_fill(finish.first, finish.cur, value);
  833.   }
  834. #       ifdef __STL_USE_EXCEPTIONS
  835.   catch(...) {
  836.     for (map_pointer n = start.node; n < cur; ++n)
  837.       destroy(*n, *n + buffer_size());
  838.     destroy_map_and_nodes();
  839.     throw;
  840.   }
  841. #       endif /* __STL_USE_EXCEPTIONS */
  842. }
  843.  
  844. #ifdef __STL_MEMBER_TEMPLATES  
  845.  
  846. template <class T, class Alloc, size_t BufSize>
  847. template <class InputIterator>
  848. void deque<T, Alloc, BufSize>::range_initialize(InputIterator first,
  849.                                                 InputIterator last,
  850.                                                 input_iterator_tag) {
  851.   create_map_and_nodes(0);
  852.   for ( ; first != last; ++first)
  853.     push_back(*first);
  854. }
  855.  
  856. template <class T, class Alloc, size_t BufSize>
  857. template <class ForwardIterator>
  858. void deque<T, Alloc, BufSize>::range_initialize(ForwardIterator first,
  859.                                                 ForwardIterator last,
  860.                                                 forward_iterator_tag) {
  861.   size_type n = 0;
  862.   distance(first, last, n);
  863.   create_map_and_nodes(n);
  864.   __STL_TRY {
  865.     uninitialized_copy(first, last, start);
  866.   }
  867.   __STL_UNWIND(destroy_map_and_nodes());
  868. }
  869.  
  870. #endif /* __STL_MEMBER_TEMPLATES */
  871.  
  872. // Called only if finish.cur == finish.last - 1.
  873. template <class T, class Alloc, size_t BufSize>
  874. void deque<T, Alloc, BufSize>::push_back_aux(const value_type& t) {
  875.   value_type t_copy = t;
  876.   reserve_map_at_back();
  877.   *(finish.node + 1) = allocate_node();
  878.   __STL_TRY {
  879.     construct(finish.cur, t_copy);
  880.     finish.set_node(finish.node + 1);
  881.     finish.cur = finish.first;
  882.   }
  883.   __STL_UNWIND(deallocate_node(*(finish.node + 1)));
  884. }
  885.  
  886. // Called only if start.cur == start.first.
  887. template <class T, class Alloc, size_t BufSize>
  888. void deque<T, Alloc, BufSize>::push_front_aux(const value_type& t) {
  889.   value_type t_copy = t;
  890.   reserve_map_at_front();
  891.   *(start.node - 1) = allocate_node();
  892.   __STL_TRY {
  893.     start.set_node(start.node - 1);
  894.     start.cur = start.last - 1;
  895.     construct(start.cur, t_copy);
  896.   }
  897. #     ifdef __STL_USE_EXCEPTIONS
  898.   catch(...) {
  899.     start.set_node(start.node + 1);
  900.     start.cur = start.first;
  901.     deallocate_node(*(start.node - 1));
  902.     throw;
  903.   }
  904. #     endif /* __STL_USE_EXCEPTIONS */
  905.  
  906. // Called only if finish.cur == finish.first.
  907. template <class T, class Alloc, size_t BufSize>
  908. void deque<T, Alloc, BufSize>:: pop_back_aux() {
  909.   deallocate_node(finish.first);
  910.   finish.set_node(finish.node - 1);
  911.   finish.cur = finish.last - 1;
  912.   destroy(finish.cur);
  913. }
  914.  
  915. // Called only if start.cur == start.last - 1.  Note that if the deque
  916. //  has at least one element (a necessary precondition for this member
  917. //  function), and if start.cur == start.last, then the deque must have
  918. //  at least two nodes.
  919. template <class T, class Alloc, size_t BufSize>
  920. void deque<T, Alloc, BufSize>::pop_front_aux() {
  921.   destroy(start.cur);
  922.   deallocate_node(start.first);
  923.   start.set_node(start.node + 1);
  924.   start.cur = start.first;
  925. }      
  926.  
  927. #ifdef __STL_MEMBER_TEMPLATES  
  928.  
  929. template <class T, class Alloc, size_t BufSize>
  930. template <class InputIterator>
  931. void deque<T, Alloc, BufSize>::insert(iterator pos,
  932.                                       InputIterator first, InputIterator last,
  933.                                       input_iterator_tag) {
  934.   copy(first, last, inserter(*this, pos));
  935. }
  936.  
  937. template <class T, class Alloc, size_t BufSize>
  938. template <class ForwardIterator>
  939. void deque<T, Alloc, BufSize>::insert(iterator pos,
  940.                                       ForwardIterator first,
  941.                                       ForwardIterator last,
  942.                                       forward_iterator_tag) {
  943.   size_type n = 0;
  944.   distance(first, last, n);
  945.   if (pos.cur == start.cur) {
  946.     iterator new_start = reserve_elements_at_front(n);
  947.     __STL_TRY {
  948.       uninitialized_copy(first, last, new_start);
  949.       start = new_start;
  950.     }
  951.     __STL_UNWIND(destroy_nodes_at_front(new_start));
  952.   }
  953.   else if (pos.cur == finish.cur) {
  954.     iterator new_finish = reserve_elements_at_back(n);
  955.     __STL_TRY {
  956.       uninitialized_copy(first, last, finish);
  957.       finish = new_finish;
  958.     }
  959.     __STL_UNWIND(destroy_nodes_at_back(new_finish));
  960.   }
  961.   else
  962.     insert_aux(pos, first, last, n);
  963. }
  964.  
  965. #endif /* __STL_MEMBER_TEMPLATES */
  966.  
  967. template <class T, class Alloc, size_t BufSize>
  968. typename deque<T, Alloc, BufSize>::iterator
  969. deque<T, Alloc, BufSize>::insert_aux(iterator pos, const value_type& x) {
  970.   difference_type index = pos - start;
  971.   value_type x_copy = x;
  972.   if (index < size() / 2) {
  973.     push_front(front());
  974.     iterator front1 = start;
  975.     ++front1;
  976.     iterator front2 = front1;
  977.     ++front2;
  978.     pos = start + index;
  979.     iterator pos1 = pos;
  980.     ++pos1;
  981.     copy(front2, pos1, front1);
  982.   }
  983.   else {
  984.     push_back(back());
  985.     iterator back1 = finish;
  986.     --back1;
  987.     iterator back2 = back1;
  988.     --back2;
  989.     pos = start + index;
  990.     copy_backward(pos, back2, back1);
  991.   }
  992.   *pos = x_copy;
  993.   return pos;
  994. }
  995.  
  996. template <class T, class Alloc, size_t BufSize>
  997. void deque<T, Alloc, BufSize>::insert_aux(iterator pos,
  998.                                           size_type n, const value_type& x) {
  999.   const difference_type elems_before = pos - start;
  1000.   size_type length = size();
  1001.   value_type x_copy = x;
  1002.   if (elems_before < length / 2) {
  1003.     iterator new_start = reserve_elements_at_front(n);
  1004.     iterator old_start = start;
  1005.     pos = start + elems_before;
  1006.     __STL_TRY {
  1007.       if (elems_before >= difference_type(n)) {
  1008.         iterator start_n = start + difference_type(n);
  1009.         uninitialized_copy(start, start_n, new_start);
  1010.         start = new_start;
  1011.         copy(start_n, pos, old_start);
  1012.         fill(pos - difference_type(n), pos, x_copy);
  1013.       }
  1014.       else {
  1015.         __uninitialized_copy_fill(start, pos, new_start, start, x_copy);
  1016.         start = new_start;
  1017.         fill(old_start, pos, x_copy);
  1018.       }
  1019.     }
  1020.     __STL_UNWIND(destroy_nodes_at_front(new_start));
  1021.   }
  1022.   else {
  1023.     iterator new_finish = reserve_elements_at_back(n);
  1024.     iterator old_finish = finish;
  1025.     const difference_type elems_after = difference_type(length) - elems_before;
  1026.     pos = finish - elems_after;
  1027.     __STL_TRY {
  1028.       if (elems_after > difference_type(n)) {
  1029.         iterator finish_n = finish - difference_type(n);
  1030.         uninitialized_copy(finish_n, finish, finish);
  1031.         finish = new_finish;
  1032.         copy_backward(pos, finish_n, old_finish);
  1033.         fill(pos, pos + difference_type(n), x_copy);
  1034.       }
  1035.       else {
  1036.         __uninitialized_fill_copy(finish, pos + difference_type(n),
  1037.                                   x_copy,
  1038.                                   pos, finish);
  1039.         finish = new_finish;
  1040.         fill(pos, old_finish, x_copy);
  1041.       }
  1042.     }
  1043.     __STL_UNWIND(destroy_nodes_at_back(new_finish));
  1044.   }
  1045. }
  1046.  
  1047. #ifdef __STL_MEMBER_TEMPLATES  
  1048.  
  1049. template <class T, class Alloc, size_t BufSize>
  1050. template <class ForwardIterator>
  1051. void deque<T, Alloc, BufSize>::insert_aux(iterator pos,
  1052.                                           ForwardIterator first,
  1053.                                           ForwardIterator last,
  1054.                                           size_type n)
  1055. {
  1056.   const difference_type elems_before = pos - start;
  1057.   size_type length = size();
  1058.   if (elems_before < length / 2) {
  1059.     iterator new_start = reserve_elements_at_front(n);
  1060.     iterator old_start = start;
  1061.     pos = start + elems_before;
  1062.     __STL_TRY {
  1063.       if (elems_before >= difference_type(n)) {
  1064.         iterator start_n = start + difference_type(n); 
  1065.         uninitialized_copy(start, start_n, new_start);
  1066.         start = new_start;
  1067.         copy(start_n, pos, old_start);
  1068.         copy(first, last, pos - difference_type(n));
  1069.       }
  1070.       else {
  1071.         ForwardIterator mid = first;
  1072.         advance(mid, difference_type(n) - elems_before);
  1073.         __uninitialized_copy_copy(start, pos, first, mid, new_start);
  1074.         start = new_start;
  1075.         copy(mid, last, old_start);
  1076.       }
  1077.     }
  1078.     __STL_UNWIND(destroy_nodes_at_front(new_start));
  1079.   }
  1080.   else {
  1081.     iterator new_finish = reserve_elements_at_back(n);
  1082.     iterator old_finish = finish;
  1083.     const difference_type elems_after = difference_type(length) - elems_before;
  1084.     pos = finish - elems_after;
  1085.     __STL_TRY {
  1086.       if (elems_after > difference_type(n)) {
  1087.         iterator finish_n = finish - difference_type(n);
  1088.         uninitialized_copy(finish_n, finish, finish);
  1089.         finish = new_finish;
  1090.         copy_backward(pos, finish_n, old_finish);
  1091.         copy(first, last, pos);
  1092.       }
  1093.       else {
  1094.         ForwardIterator mid = first;
  1095.         advance(mid, elems_after);
  1096.         __uninitialized_copy_copy(mid, last, pos, finish, finish);
  1097.         finish = new_finish;
  1098.         copy(first, mid, pos);
  1099.       }
  1100.     }
  1101.     __STL_UNWIND(destroy_nodes_at_back(new_finish));
  1102.   }
  1103. }
  1104.  
  1105. #else /* __STL_MEMBER_TEMPLATES */
  1106.  
  1107. template <class T, class Alloc, size_t BufSize>
  1108. void deque<T, Alloc, BufSize>::insert_aux(iterator pos,
  1109.                                           const value_type* first,
  1110.                                           const value_type* last,
  1111.                                           size_type n)
  1112. {
  1113.   const difference_type elems_before = pos - start;
  1114.   size_type length = size();
  1115.   if (elems_before < length / 2) {
  1116.     iterator new_start = reserve_elements_at_front(n);
  1117.     iterator old_start = start;
  1118.     pos = start + elems_before;
  1119.     __STL_TRY {
  1120.       if (elems_before >= difference_type(n)) {
  1121.         iterator start_n = start + difference_type(n);
  1122.         uninitialized_copy(start, start_n, new_start);
  1123.         start = new_start;
  1124.         copy(start_n, pos, old_start);
  1125.         copy(first, last, pos - difference_type(n));
  1126.       }
  1127.       else {
  1128.         const value_type* mid = first + (difference_type(n) - elems_before);
  1129.         __uninitialized_copy_copy(start, pos, first, mid, new_start);
  1130.         start = new_start;
  1131.         copy(mid, last, old_start);
  1132.       }
  1133.     }
  1134.     __STL_UNWIND(destroy_nodes_at_front(new_start));
  1135.   }
  1136.   else {
  1137.     iterator new_finish = reserve_elements_at_back(n);
  1138.     iterator old_finish = finish;
  1139.     const difference_type elems_after = difference_type(length) - elems_before;
  1140.     pos = finish - elems_after;
  1141.     __STL_TRY {
  1142.       if (elems_after > difference_type(n)) {
  1143.         iterator finish_n = finish - difference_type(n);
  1144.         uninitialized_copy(finish_n, finish, finish);
  1145.         finish = new_finish;
  1146.         copy_backward(pos, finish_n, old_finish);
  1147.         copy(first, last, pos);
  1148.       }
  1149.       else {
  1150.         const value_type* mid = first + elems_after;
  1151.         __uninitialized_copy_copy(mid, last, pos, finish, finish);
  1152.         finish = new_finish;
  1153.         copy(first, mid, pos);
  1154.       }
  1155.     }
  1156.     __STL_UNWIND(destroy_nodes_at_back(new_finish));
  1157.   }
  1158. }
  1159.  
  1160. template <class T, class Alloc, size_t BufSize>
  1161. void deque<T, Alloc, BufSize>::insert_aux(iterator pos,
  1162.                                           const_iterator first,
  1163.                                           const_iterator last,
  1164.                                           size_type n)
  1165. {
  1166.   const difference_type elems_before = pos - start;
  1167.   size_type length = size();
  1168.   if (elems_before < length / 2) {
  1169.     iterator new_start = reserve_elements_at_front(n);
  1170.     iterator old_start = start;
  1171.     pos = start + elems_before;
  1172.     __STL_TRY {
  1173.       if (elems_before >= n) {
  1174.         iterator start_n = start + n;
  1175.         uninitialized_copy(start, start_n, new_start);
  1176.         start = new_start;
  1177.         copy(start_n, pos, old_start);
  1178.         copy(first, last, pos - difference_type(n));
  1179.       }
  1180.       else {
  1181.         const_iterator mid = first + (n - elems_before);
  1182.         __uninitialized_copy_copy(start, pos, first, mid, new_start);
  1183.         start = new_start;
  1184.         copy(mid, last, old_start);
  1185.       }
  1186.     }
  1187.     __STL_UNWIND(destroy_nodes_at_front(new_start));
  1188.   }
  1189.   else {
  1190.     iterator new_finish = reserve_elements_at_back(n);
  1191.     iterator old_finish = finish;
  1192.     const difference_type elems_after = length - elems_before;
  1193.     pos = finish - elems_after;
  1194.     __STL_TRY {
  1195.       if (elems_after > n) {
  1196.         iterator finish_n = finish - difference_type(n);
  1197.         uninitialized_copy(finish_n, finish, finish);
  1198.         finish = new_finish;
  1199.         copy_backward(pos, finish_n, old_finish);
  1200.         copy(first, last, pos);
  1201.       }
  1202.       else {
  1203.         const_iterator mid = first + elems_after;
  1204.         __uninitialized_copy_copy(mid, last, pos, finish, finish);
  1205.         finish = new_finish;
  1206.         copy(first, mid, pos);
  1207.       }
  1208.     }
  1209.     __STL_UNWIND(destroy_nodes_at_back(new_finish));
  1210.   }
  1211. }
  1212.  
  1213. #endif /* __STL_MEMBER_TEMPLATES */
  1214.  
  1215. template <class T, class Alloc, size_t BufSize>
  1216. void deque<T, Alloc, BufSize>::new_elements_at_front(size_type new_elements) {
  1217.   size_type new_nodes = (new_elements + buffer_size() - 1) / buffer_size();
  1218.   reserve_map_at_front(new_nodes);
  1219.   size_type i;
  1220.   __STL_TRY {
  1221.     for (i = 1; i <= new_nodes; ++i)
  1222.       *(start.node - i) = allocate_node();
  1223.   }
  1224. #       ifdef __STL_USE_EXCEPTIONS
  1225.   catch(...) {
  1226.     for (size_type j = 1; j < i; ++j)
  1227.       deallocate_node(*(start.node - j));      
  1228.     throw;
  1229.   }
  1230. #       endif /* __STL_USE_EXCEPTIONS */
  1231. }
  1232.  
  1233. template <class T, class Alloc, size_t BufSize>
  1234. void deque<T, Alloc, BufSize>::new_elements_at_back(size_type new_elements) {
  1235.   size_type new_nodes = (new_elements + buffer_size() - 1) / buffer_size();
  1236.   reserve_map_at_back(new_nodes);
  1237.   size_type i;
  1238.   __STL_TRY {
  1239.     for (i = 1; i <= new_nodes; ++i)
  1240.       *(finish.node + i) = allocate_node();
  1241.   }
  1242. #       ifdef __STL_USE_EXCEPTIONS
  1243.   catch(...) {
  1244.     for (size_type j = 1; j < i; ++j)
  1245.       deallocate_node(*(finish.node + j));      
  1246.     throw;
  1247.   }
  1248. #       endif /* __STL_USE_EXCEPTIONS */
  1249. }
  1250.  
  1251. template <class T, class Alloc, size_t BufSize>
  1252. void deque<T, Alloc, BufSize>::destroy_nodes_at_front(iterator before_start) {
  1253.   for (map_pointer n = before_start.node; n < start.node; ++n)
  1254.     deallocate_node(*n);
  1255. }
  1256.  
  1257. template <class T, class Alloc, size_t BufSize>
  1258. void deque<T, Alloc, BufSize>::destroy_nodes_at_back(iterator after_finish) {
  1259.   for (map_pointer n = after_finish.node; n > finish.node; --n)
  1260.     deallocate_node(*n);
  1261. }
  1262.  
  1263. template <class T, class Alloc, size_t BufSize>
  1264. void deque<T, Alloc, BufSize>::reallocate_map(size_type nodes_to_add,
  1265.                                               bool add_at_front) {
  1266.   size_type old_num_nodes = finish.node - start.node + 1;
  1267.   size_type new_num_nodes = old_num_nodes + nodes_to_add;
  1268.  
  1269.   map_pointer new_nstart;
  1270.   if (map_size > 2 * new_num_nodes) {
  1271.     new_nstart = map + (map_size - new_num_nodes) / 2 
  1272.                      + (add_at_front ? nodes_to_add : 0);
  1273.     if (new_nstart < start.node)
  1274.       copy(start.node, finish.node + 1, new_nstart);
  1275.     else
  1276.       copy_backward(start.node, finish.node + 1, new_nstart + old_num_nodes);
  1277.   }
  1278.   else {
  1279.     size_type new_map_size = map_size + max(map_size, nodes_to_add) + 2;
  1280.  
  1281.     map_pointer new_map = map_allocator::allocate(new_map_size);
  1282.     new_nstart = new_map + (new_map_size - new_num_nodes) / 2
  1283.                          + (add_at_front ? nodes_to_add : 0);
  1284.     copy(start.node, finish.node + 1, new_nstart);
  1285.     map_allocator::deallocate(map, map_size);
  1286.  
  1287.     map = new_map;
  1288.     map_size = new_map_size;
  1289.   }
  1290.  
  1291.   start.set_node(new_nstart);
  1292.   finish.set_node(new_nstart + old_num_nodes - 1);
  1293. }
  1294.  
  1295.  
  1296. // Nonmember functions.
  1297.  
  1298. #ifndef __STL_NON_TYPE_TMPL_PARAM_BUG
  1299.  
  1300. template <class T, class Alloc, size_t BufSiz>
  1301. bool operator==(const deque<T, Alloc, BufSiz>& x,
  1302.                 const deque<T, Alloc, BufSiz>& y) {
  1303.   return x.size() == y.size() && equal(x.begin(), x.end(), y.begin());
  1304. }
  1305.  
  1306. template <class T, class Alloc, size_t BufSiz>
  1307. bool operator<(const deque<T, Alloc, BufSiz>& x,
  1308.                const deque<T, Alloc, BufSiz>& y) {
  1309.   return lexicographical_compare(x.begin(), x.end(), y.begin(), y.end());
  1310. }
  1311.  
  1312. #endif /* __STL_NON_TYPE_TMPL_PARAM_BUG */
  1313.  
  1314. #if defined(__STL_FUNCTION_TMPL_PARTIAL_ORDER) && \
  1315.     !defined(__STL_NON_TYPE_TMPL_PARAM_BUG)
  1316.  
  1317. template <class T, class Alloc, size_t BufSiz>
  1318. inline void swap(deque<T, Alloc, BufSiz>& x, deque<T, Alloc, BufSiz>& y) {
  1319.   x.swap(y);
  1320. }
  1321.  
  1322. #endif
  1323.  
  1324. #if defined(__sgi) && !defined(__GNUC__) && (_MIPS_SIM != _MIPS_SIM_ABI32)
  1325. #pragma reset woff 1174
  1326. #endif
  1327.           
  1328. __STL_END_NAMESPACE 
  1329.   
  1330. #endif /* __SGI_STL_INTERNAL_DEQUE_H */
  1331.  
  1332. // Local Variables:
  1333. // mode:C++
  1334. // End:
  1335.