Restore the "GPL licensing not permitted" in GLUT license headers.
[haiku.git] / headers / cpp / stl_slist.h
blob6da234d92c2cadf5ac2c7732b5a3d7fb3527aa5f
1 /*
2 * Copyright (c) 1997
3 * Silicon Graphics Computer Systems, Inc.
5 * Permission to use, copy, modify, distribute and sell this software
6 * and its documentation for any purpose is hereby granted without fee,
7 * provided that the above copyright notice appear in all copies and
8 * that both that copyright notice and this permission notice appear
9 * in supporting documentation. Silicon Graphics makes no
10 * representations about the suitability of this software for any
11 * purpose. It is provided "as is" without express or implied warranty.
15 /* NOTE: This is an internal header file, included by other STL headers.
16 * You should not attempt to use it directly.
19 #ifndef __SGI_STL_INTERNAL_SLIST_H
20 #define __SGI_STL_INTERNAL_SLIST_H
23 __STL_BEGIN_NAMESPACE
25 #if defined(__sgi) && !defined(__GNUC__) && (_MIPS_SIM != _MIPS_SIM_ABI32)
26 #pragma set woff 1174
27 #pragma set woff 1375
28 #endif
30 struct _Slist_node_base
32 _Slist_node_base* _M_next;
35 inline _Slist_node_base*
36 __slist_make_link(_Slist_node_base* __prev_node,
37 _Slist_node_base* __new_node)
39 __new_node->_M_next = __prev_node->_M_next;
40 __prev_node->_M_next = __new_node;
41 return __new_node;
44 inline _Slist_node_base*
45 __slist_previous(_Slist_node_base* __head,
46 const _Slist_node_base* __node)
48 while (__head && __head->_M_next != __node)
49 __head = __head->_M_next;
50 return __head;
53 inline const _Slist_node_base*
54 __slist_previous(const _Slist_node_base* __head,
55 const _Slist_node_base* __node)
57 while (__head && __head->_M_next != __node)
58 __head = __head->_M_next;
59 return __head;
62 inline void __slist_splice_after(_Slist_node_base* __pos,
63 _Slist_node_base* __before_first,
64 _Slist_node_base* __before_last)
66 if (__pos != __before_first && __pos != __before_last) {
67 _Slist_node_base* __first = __before_first->_M_next;
68 _Slist_node_base* __after = __pos->_M_next;
69 __before_first->_M_next = __before_last->_M_next;
70 __pos->_M_next = __first;
71 __before_last->_M_next = __after;
75 inline _Slist_node_base* __slist_reverse(_Slist_node_base* __node)
77 _Slist_node_base* __result = __node;
78 __node = __node->_M_next;
79 __result->_M_next = 0;
80 while(__node) {
81 _Slist_node_base* __next = __node->_M_next;
82 __node->_M_next = __result;
83 __result = __node;
84 __node = __next;
86 return __result;
89 inline size_t __slist_size(_Slist_node_base* __node)
91 size_t __result = 0;
92 for ( ; __node != 0; __node = __node->_M_next)
93 ++__result;
94 return __result;
97 template <class _Tp>
98 struct _Slist_node : public _Slist_node_base
100 _Tp _M_data;
103 struct _Slist_iterator_base
105 typedef size_t size_type;
106 typedef ptrdiff_t difference_type;
107 typedef forward_iterator_tag iterator_category;
109 _Slist_node_base* _M_node;
111 _Slist_iterator_base(_Slist_node_base* __x) : _M_node(__x) {}
112 void _M_incr() { _M_node = _M_node->_M_next; }
114 bool operator==(const _Slist_iterator_base& __x) const {
115 return _M_node == __x._M_node;
117 bool operator!=(const _Slist_iterator_base& __x) const {
118 return _M_node != __x._M_node;
122 template <class _Tp, class _Ref, class _Ptr>
123 struct _Slist_iterator : public _Slist_iterator_base
125 typedef _Slist_iterator<_Tp, _Tp&, _Tp*> iterator;
126 typedef _Slist_iterator<_Tp, const _Tp&, const _Tp*> const_iterator;
127 typedef _Slist_iterator<_Tp, _Ref, _Ptr> _Self;
129 typedef _Tp value_type;
130 typedef _Ptr pointer;
131 typedef _Ref reference;
132 typedef _Slist_node<_Tp> _Node;
134 _Slist_iterator(_Node* __x) : _Slist_iterator_base(__x) {}
135 _Slist_iterator() : _Slist_iterator_base(0) {}
136 _Slist_iterator(const iterator& __x) : _Slist_iterator_base(__x._M_node) {}
138 reference operator*() const { return ((_Node*) _M_node)->_M_data; }
139 #ifndef __SGI_STL_NO_ARROW_OPERATOR
140 pointer operator->() const { return &(operator*()); }
141 #endif /* __SGI_STL_NO_ARROW_OPERATOR */
143 _Self& operator++()
145 _M_incr();
146 return *this;
148 _Self operator++(int)
150 _Self __tmp = *this;
151 _M_incr();
152 return __tmp;
156 #ifndef __STL_CLASS_PARTIAL_SPECIALIZATION
158 inline ptrdiff_t* distance_type(const _Slist_iterator_base&) {
159 return 0;
162 inline forward_iterator_tag iterator_category(const _Slist_iterator_base&) {
163 return forward_iterator_tag();
166 template <class _Tp, class _Ref, class _Ptr>
167 inline _Tp* value_type(const _Slist_iterator<_Tp, _Ref, _Ptr>&) {
168 return 0;
171 #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */
173 // Base class that encapsulates details of allocators. Three cases:
174 // an ordinary standard-conforming allocator, a standard-conforming
175 // allocator with no non-static data, and an SGI-style allocator.
176 // This complexity is necessary only because we're worrying about backward
177 // compatibility and because we want to avoid wasting storage on an
178 // allocator instance if it isn't necessary.
180 #ifdef __STL_USE_STD_ALLOCATORS
182 // Base for general standard-conforming allocators.
183 template <class _Tp, class _Allocator, bool _IsStatic>
184 class _Slist_alloc_base {
185 public:
186 typedef typename _Alloc_traits<_Tp,_Allocator>::allocator_type
187 allocator_type;
188 allocator_type get_allocator() const { return _M_node_allocator; }
190 _Slist_alloc_base(const allocator_type& __a) : _M_node_allocator(__a) {}
192 protected:
193 _Slist_node<_Tp>* _M_get_node()
194 { return _M_node_allocator.allocate(1); }
195 void _M_put_node(_Slist_node<_Tp>* __p)
196 { _M_node_allocator.deallocate(__p, 1); }
198 protected:
199 typename _Alloc_traits<_Slist_node<_Tp>,_Allocator>::allocator_type
200 _M_node_allocator;
201 _Slist_node_base _M_head;
204 // Specialization for instanceless allocators.
205 template <class _Tp, class _Allocator>
206 class _Slist_alloc_base<_Tp,_Allocator, true> {
207 public:
208 typedef typename _Alloc_traits<_Tp,_Allocator>::allocator_type
209 allocator_type;
210 allocator_type get_allocator() const { return allocator_type(); }
212 _Slist_alloc_base(const allocator_type&) {}
214 protected:
215 typedef typename _Alloc_traits<_Slist_node<_Tp>, _Allocator>::_Alloc_type
216 _Alloc_type;
217 _Slist_node<_Tp>* _M_get_node() { return _Alloc_type::allocate(1); }
218 void _M_put_node(_Slist_node<_Tp>* __p) { _Alloc_type::deallocate(__p, 1); }
220 protected:
221 _Slist_node_base _M_head;
225 template <class _Tp, class _Alloc>
226 struct _Slist_base
227 : public _Slist_alloc_base<_Tp, _Alloc,
228 _Alloc_traits<_Tp, _Alloc>::_S_instanceless>
230 typedef _Slist_alloc_base<_Tp, _Alloc,
231 _Alloc_traits<_Tp, _Alloc>::_S_instanceless>
232 _Base;
233 typedef typename _Base::allocator_type allocator_type;
235 _Slist_base(const allocator_type& __a) : _Base(__a) { _M_head._M_next = 0; }
236 ~_Slist_base() { _M_erase_after(&_M_head, 0); }
238 protected:
240 _Slist_node_base* _M_erase_after(_Slist_node_base* __pos)
242 _Slist_node<_Tp>* __next = (_Slist_node<_Tp>*) (__pos->_M_next);
243 _Slist_node_base* __next_next = __next->_M_next;
244 __pos->_M_next = __next_next;
245 destroy(&__next->_M_data);
246 _M_put_node(__next);
247 return __next_next;
249 _Slist_node_base* _M_erase_after(_Slist_node_base*, _Slist_node_base*);
252 #else /* __STL_USE_STD_ALLOCATORS */
254 template <class _Tp, class _Alloc>
255 struct _Slist_base {
256 typedef _Alloc allocator_type;
257 allocator_type get_allocator() const { return allocator_type(); }
259 _Slist_base(const allocator_type&) { _M_head._M_next = 0; }
260 ~_Slist_base() { _M_erase_after(&_M_head, 0); }
262 protected:
263 typedef simple_alloc<_Slist_node<_Tp>, _Alloc> _Alloc_type;
264 _Slist_node<_Tp>* _M_get_node() { return _Alloc_type::allocate(1); }
265 void _M_put_node(_Slist_node<_Tp>* __p) { _Alloc_type::deallocate(__p, 1); }
267 _Slist_node_base* _M_erase_after(_Slist_node_base* __pos)
269 _Slist_node<_Tp>* __next = (_Slist_node<_Tp>*) (__pos->_M_next);
270 _Slist_node_base* __next_next = __next->_M_next;
271 __pos->_M_next = __next_next;
272 destroy(&__next->_M_data);
273 _M_put_node(__next);
274 return __next_next;
276 _Slist_node_base* _M_erase_after(_Slist_node_base*, _Slist_node_base*);
278 protected:
279 _Slist_node_base _M_head;
282 #endif /* __STL_USE_STD_ALLOCATORS */
284 template <class _Tp, class _Alloc>
285 _Slist_node_base*
286 _Slist_base<_Tp,_Alloc>::_M_erase_after(_Slist_node_base* __before_first,
287 _Slist_node_base* __last_node) {
288 _Slist_node<_Tp>* __cur = (_Slist_node<_Tp>*) (__before_first->_M_next);
289 while (__cur != __last_node) {
290 _Slist_node<_Tp>* __tmp = __cur;
291 __cur = (_Slist_node<_Tp>*) __cur->_M_next;
292 destroy(&__tmp->_M_data);
293 _M_put_node(__tmp);
295 __before_first->_M_next = __last_node;
296 return __last_node;
299 template <class _Tp, class _Alloc = __STL_DEFAULT_ALLOCATOR(_Tp) >
300 class slist : private _Slist_base<_Tp,_Alloc>
302 private:
303 typedef _Slist_base<_Tp,_Alloc> _Base;
304 public:
305 typedef _Tp value_type;
306 typedef value_type* pointer;
307 typedef const value_type* const_pointer;
308 typedef value_type& reference;
309 typedef const value_type& const_reference;
310 typedef size_t size_type;
311 typedef ptrdiff_t difference_type;
313 typedef _Slist_iterator<_Tp, _Tp&, _Tp*> iterator;
314 typedef _Slist_iterator<_Tp, const _Tp&, const _Tp*> const_iterator;
316 typedef typename _Base::allocator_type allocator_type;
317 allocator_type get_allocator() const { return _Base::get_allocator(); }
319 private:
320 typedef _Slist_node<_Tp> _Node;
321 typedef _Slist_node_base _Node_base;
322 typedef _Slist_iterator_base _Iterator_base;
324 _Node* _M_create_node(const value_type& __x) {
325 _Node* __node = _M_get_node();
326 __STL_TRY {
327 construct(&__node->_M_data, __x);
328 __node->_M_next = 0;
330 __STL_UNWIND(_M_put_node(__node));
331 return __node;
334 _Node* _M_create_node() {
335 _Node* __node = _M_get_node();
336 __STL_TRY {
337 construct(&__node->_M_data);
338 __node->_M_next = 0;
340 __STL_UNWIND(_M_put_node(__node));
341 return __node;
344 private:
345 #ifdef __STL_USE_NAMESPACES
346 using _Base::_M_get_node;
347 using _Base::_M_put_node;
348 using _Base::_M_erase_after;
349 using _Base::_M_head;
350 #endif /* __STL_USE_NAMESPACES */
352 public:
353 explicit slist(const allocator_type& __a = allocator_type()) : _Base(__a) {}
355 slist(size_type __n, const value_type& __x,
356 const allocator_type& __a = allocator_type()) : _Base(__a)
357 { _M_insert_after_fill(&_M_head, __n, __x); }
359 explicit slist(size_type __n) : _Base(allocator_type())
360 { _M_insert_after_fill(&_M_head, __n, value_type()); }
362 #ifdef __STL_MEMBER_TEMPLATES
363 // We don't need any dispatching tricks here, because _M_insert_after_range
364 // already does them.
365 template <class _InputIterator>
366 slist(_InputIterator __first, _InputIterator __last,
367 const allocator_type& __a = allocator_type()) : _Base(__a)
368 { _M_insert_after_range(&_M_head, __first, __last); }
370 #else /* __STL_MEMBER_TEMPLATES */
371 slist(const_iterator __first, const_iterator __last,
372 const allocator_type& __a = allocator_type()) : _Base(__a)
373 { _M_insert_after_range(&_M_head, __first, __last); }
374 slist(const value_type* __first, const value_type* __last,
375 const allocator_type& __a = allocator_type()) : _Base(__a)
376 { _M_insert_after_range(&_M_head, __first, __last); }
377 #endif /* __STL_MEMBER_TEMPLATES */
379 slist(const slist& __x) : _Base(__x.get_allocator())
380 { _M_insert_after_range(&_M_head, __x.begin(), __x.end()); }
382 slist& operator= (const slist& __x);
384 ~slist() {}
386 public:
387 // assign(), a generalized assignment member function. Two
388 // versions: one that takes a count, and one that takes a range.
389 // The range version is a member template, so we dispatch on whether
390 // or not the type is an integer.
392 void assign(size_type __n, const _Tp& __val);
394 #ifdef __STL_MEMBER_TEMPLATES
396 template <class _InputIterator>
397 void assign(_InputIterator __first, _InputIterator __last) {
398 typedef typename _Is_integer<_InputIterator>::_Integral _Integral;
399 _M_assign_dispatch(__first, __last, _Integral());
402 template <class _Integer>
403 void _M_assign_dispatch(_Integer __n, _Integer __val, __true_type)
404 { assign((size_type) __n, (_Tp) __val); }
406 template <class _InputIterator>
407 void _M_assign_dispatch(_InputIterator __first, _InputIterator __last,
408 __false_type);
410 #endif /* __STL_MEMBER_TEMPLATES */
412 public:
414 iterator begin() { return iterator((_Node*)_M_head._M_next); }
415 const_iterator begin() const
416 { return const_iterator((_Node*)_M_head._M_next);}
418 iterator end() { return iterator(0); }
419 const_iterator end() const { return const_iterator(0); }
421 size_type size() const { return __slist_size(_M_head._M_next); }
423 size_type max_size() const { return size_type(-1); }
425 bool empty() const { return _M_head._M_next == 0; }
427 void swap(slist& __x) { __STD::swap(_M_head._M_next, __x._M_head._M_next); }
429 public:
430 friend bool operator== __STL_NULL_TMPL_ARGS (const slist<_Tp,_Alloc>& _SL1,
431 const slist<_Tp,_Alloc>& _SL2);
433 public:
435 reference front() { return ((_Node*) _M_head._M_next)->_M_data; }
436 const_reference front() const
437 { return ((_Node*) _M_head._M_next)->_M_data; }
438 void push_front(const value_type& __x) {
439 __slist_make_link(&_M_head, _M_create_node(__x));
441 void push_front() { __slist_make_link(&_M_head, _M_create_node());}
442 void pop_front() {
443 _Node* __node = (_Node*) _M_head._M_next;
444 _M_head._M_next = __node->_M_next;
445 destroy(&__node->_M_data);
446 _M_put_node(__node);
449 iterator previous(const_iterator __pos) {
450 return iterator((_Node*) __slist_previous(&_M_head, __pos._M_node));
452 const_iterator previous(const_iterator __pos) const {
453 return const_iterator((_Node*) __slist_previous(&_M_head, __pos._M_node));
456 private:
457 _Node* _M_insert_after(_Node_base* __pos, const value_type& __x) {
458 return (_Node*) (__slist_make_link(__pos, _M_create_node(__x)));
461 _Node* _M_insert_after(_Node_base* __pos) {
462 return (_Node*) (__slist_make_link(__pos, _M_create_node()));
465 void _M_insert_after_fill(_Node_base* __pos,
466 size_type __n, const value_type& __x) {
467 for (size_type __i = 0; __i < __n; ++__i)
468 __pos = __slist_make_link(__pos, _M_create_node(__x));
471 #ifdef __STL_MEMBER_TEMPLATES
473 // Check whether it's an integral type. If so, it's not an iterator.
474 template <class _InIter>
475 void _M_insert_after_range(_Node_base* __pos,
476 _InIter __first, _InIter __last) {
477 typedef typename _Is_integer<_InIter>::_Integral _Integral;
478 _M_insert_after_range(__pos, __first, __last, _Integral());
481 template <class _Integer>
482 void _M_insert_after_range(_Node_base* __pos, _Integer __n, _Integer __x,
483 __true_type) {
484 _M_insert_after_fill(__pos, __n, __x);
487 template <class _InIter>
488 void _M_insert_after_range(_Node_base* __pos,
489 _InIter __first, _InIter __last,
490 __false_type) {
491 while (__first != __last) {
492 __pos = __slist_make_link(__pos, _M_create_node(*__first));
493 ++__first;
497 #else /* __STL_MEMBER_TEMPLATES */
499 void _M_insert_after_range(_Node_base* __pos,
500 const_iterator __first, const_iterator __last) {
501 while (__first != __last) {
502 __pos = __slist_make_link(__pos, _M_create_node(*__first));
503 ++__first;
506 void _M_insert_after_range(_Node_base* __pos,
507 const value_type* __first,
508 const value_type* __last) {
509 while (__first != __last) {
510 __pos = __slist_make_link(__pos, _M_create_node(*__first));
511 ++__first;
515 #endif /* __STL_MEMBER_TEMPLATES */
517 public:
519 iterator insert_after(iterator __pos, const value_type& __x) {
520 return iterator(_M_insert_after(__pos._M_node, __x));
523 iterator insert_after(iterator __pos) {
524 return insert_after(__pos, value_type());
527 void insert_after(iterator __pos, size_type __n, const value_type& __x) {
528 _M_insert_after_fill(__pos._M_node, __n, __x);
531 #ifdef __STL_MEMBER_TEMPLATES
533 // We don't need any dispatching tricks here, because _M_insert_after_range
534 // already does them.
535 template <class _InIter>
536 void insert_after(iterator __pos, _InIter __first, _InIter __last) {
537 _M_insert_after_range(__pos._M_node, __first, __last);
540 #else /* __STL_MEMBER_TEMPLATES */
542 void insert_after(iterator __pos,
543 const_iterator __first, const_iterator __last) {
544 _M_insert_after_range(__pos._M_node, __first, __last);
546 void insert_after(iterator __pos,
547 const value_type* __first, const value_type* __last) {
548 _M_insert_after_range(__pos._M_node, __first, __last);
551 #endif /* __STL_MEMBER_TEMPLATES */
553 iterator insert(iterator __pos, const value_type& __x) {
554 return iterator(_M_insert_after(__slist_previous(&_M_head, __pos._M_node),
555 __x));
558 iterator insert(iterator __pos) {
559 return iterator(_M_insert_after(__slist_previous(&_M_head, __pos._M_node),
560 value_type()));
563 void insert(iterator __pos, size_type __n, const value_type& __x) {
564 _M_insert_after_fill(__slist_previous(&_M_head, __pos._M_node), __n, __x);
567 #ifdef __STL_MEMBER_TEMPLATES
569 // We don't need any dispatching tricks here, because _M_insert_after_range
570 // already does them.
571 template <class _InIter>
572 void insert(iterator __pos, _InIter __first, _InIter __last) {
573 _M_insert_after_range(__slist_previous(&_M_head, __pos._M_node),
574 __first, __last);
577 #else /* __STL_MEMBER_TEMPLATES */
579 void insert(iterator __pos, const_iterator __first, const_iterator __last) {
580 _M_insert_after_range(__slist_previous(&_M_head, __pos._M_node),
581 __first, __last);
583 void insert(iterator __pos, const value_type* __first,
584 const value_type* __last) {
585 _M_insert_after_range(__slist_previous(&_M_head, __pos._M_node),
586 __first, __last);
589 #endif /* __STL_MEMBER_TEMPLATES */
592 public:
593 iterator erase_after(iterator __pos) {
594 return iterator((_Node*) _M_erase_after(__pos._M_node));
596 iterator erase_after(iterator __before_first, iterator __last) {
597 return iterator((_Node*) _M_erase_after(__before_first._M_node,
598 __last._M_node));
601 iterator erase(iterator __pos) {
602 return (_Node*) _M_erase_after(__slist_previous(&_M_head,
603 __pos._M_node));
605 iterator erase(iterator __first, iterator __last) {
606 return (_Node*) _M_erase_after(
607 __slist_previous(&_M_head, __first._M_node), __last._M_node);
610 void resize(size_type new_size, const _Tp& __x);
611 void resize(size_type new_size) { resize(new_size, _Tp()); }
612 void clear() { _M_erase_after(&_M_head, 0); }
614 public:
615 // Moves the range [__before_first + 1, __before_last + 1) to *this,
616 // inserting it immediately after __pos. This is constant time.
617 void splice_after(iterator __pos,
618 iterator __before_first, iterator __before_last)
620 if (__before_first != __before_last)
621 __slist_splice_after(__pos._M_node, __before_first._M_node,
622 __before_last._M_node);
625 // Moves the element that follows __prev to *this, inserting it immediately
626 // after __pos. This is constant time.
627 void splice_after(iterator __pos, iterator __prev)
629 __slist_splice_after(__pos._M_node,
630 __prev._M_node, __prev._M_node->_M_next);
634 // Linear in distance(begin(), __pos), and linear in __x.size().
635 void splice(iterator __pos, slist& __x) {
636 if (__x._M_head._M_next)
637 __slist_splice_after(__slist_previous(&_M_head, __pos._M_node),
638 &__x._M_head, __slist_previous(&__x._M_head, 0));
641 // Linear in distance(begin(), __pos), and in distance(__x.begin(), __i).
642 void splice(iterator __pos, slist& __x, iterator __i) {
643 __slist_splice_after(__slist_previous(&_M_head, __pos._M_node),
644 __slist_previous(&__x._M_head, __i._M_node),
645 __i._M_node);
648 // Linear in distance(begin(), __pos), in distance(__x.begin(), __first),
649 // and in distance(__first, __last).
650 void splice(iterator __pos, slist& __x, iterator __first, iterator __last)
652 if (__first != __last)
653 __slist_splice_after(__slist_previous(&_M_head, __pos._M_node),
654 __slist_previous(&__x._M_head, __first._M_node),
655 __slist_previous(__first._M_node, __last._M_node));
658 public:
659 void reverse() {
660 if (_M_head._M_next)
661 _M_head._M_next = __slist_reverse(_M_head._M_next);
664 void remove(const _Tp& __val);
665 void unique();
666 void merge(slist& __x);
667 void sort();
669 #ifdef __STL_MEMBER_TEMPLATES
670 template <class _Predicate>
671 void remove_if(_Predicate __pred);
673 template <class _BinaryPredicate>
674 void unique(_BinaryPredicate __pred);
676 template <class _StrictWeakOrdering>
677 void merge(slist&, _StrictWeakOrdering);
679 template <class _StrictWeakOrdering>
680 void sort(_StrictWeakOrdering __comp);
681 #endif /* __STL_MEMBER_TEMPLATES */
684 template <class _Tp, class _Alloc>
685 slist<_Tp,_Alloc>& slist<_Tp,_Alloc>::operator=(const slist<_Tp,_Alloc>& __x)
687 if (&__x != this) {
688 _Node_base* __p1 = &_M_head;
689 _Node* __n1 = (_Node*) _M_head._M_next;
690 const _Node* __n2 = (const _Node*) __x._M_head._M_next;
691 while (__n1 && __n2) {
692 __n1->_M_data = __n2->_M_data;
693 __p1 = __n1;
694 __n1 = (_Node*) __n1->_M_next;
695 __n2 = (const _Node*) __n2->_M_next;
697 if (__n2 == 0)
698 _M_erase_after(__p1, 0);
699 else
700 _M_insert_after_range(__p1, const_iterator((_Node*)__n2),
701 const_iterator(0));
703 return *this;
706 template <class _Tp, class _Alloc>
707 void slist<_Tp, _Alloc>::assign(size_type __n, const _Tp& __val) {
708 _Node_base* __prev = &_M_head;
709 _Node* __node = (_Node*) _M_head._M_next;
710 for ( ; __node != 0 && __n > 0 ; --__n) {
711 __node->_M_data = __val;
712 __prev = __node;
713 __node = (_Node*) __node->_M_next;
715 if (__n > 0)
716 _M_insert_after_fill(__prev, __n, __val);
717 else
718 _M_erase_after(__prev, 0);
721 #ifdef __STL_MEMBER_TEMPLATES
723 template <class _Tp, class _Alloc> template <class _InputIter>
724 void
725 slist<_Tp, _Alloc>::_M_assign_dispatch(_InputIter __first, _InputIter __last,
726 __false_type)
728 _Node_base* __prev = &_M_head;
729 _Node* __node = (_Node*) _M_head._M_next;
730 while (__node != 0 && __first != __last) {
731 __node->_M_data = *__first;
732 __prev = __node;
733 __node = (_Node*) __node->_M_next;
734 ++__first;
736 if (__first != __last)
737 _M_insert_after_range(__prev, __first, __last);
738 else
739 _M_erase_after(__prev, 0);
742 #endif /* __STL_MEMBER_TEMPLATES */
744 template <class _Tp, class _Alloc>
745 inline bool
746 operator==(const slist<_Tp,_Alloc>& _SL1, const slist<_Tp,_Alloc>& _SL2)
748 typedef typename slist<_Tp,_Alloc>::_Node _Node;
749 _Node* __n1 = (_Node*) _SL1._M_head._M_next;
750 _Node* __n2 = (_Node*) _SL2._M_head._M_next;
751 while (__n1 && __n2 && __n1->_M_data == __n2->_M_data) {
752 __n1 = (_Node*) __n1->_M_next;
753 __n2 = (_Node*) __n2->_M_next;
755 return __n1 == 0 && __n2 == 0;
758 template <class _Tp, class _Alloc>
759 inline bool operator<(const slist<_Tp,_Alloc>& _SL1,
760 const slist<_Tp,_Alloc>& _SL2)
762 return lexicographical_compare(_SL1.begin(), _SL1.end(),
763 _SL2.begin(), _SL2.end());
766 #ifdef __STL_FUNCTION_TMPL_PARTIAL_ORDER
768 template <class _Tp, class _Alloc>
769 inline void swap(slist<_Tp,_Alloc>& __x, slist<_Tp,_Alloc>& __y) {
770 __x.swap(__y);
773 #endif /* __STL_FUNCTION_TMPL_PARTIAL_ORDER */
776 template <class _Tp, class _Alloc>
777 void slist<_Tp,_Alloc>::resize(size_type __len, const _Tp& __x)
779 _Node_base* __cur = &_M_head;
780 while (__cur->_M_next != 0 && __len > 0) {
781 --__len;
782 __cur = __cur->_M_next;
784 if (__cur->_M_next)
785 _M_erase_after(__cur, 0);
786 else
787 _M_insert_after_fill(__cur, __len, __x);
790 template <class _Tp, class _Alloc>
791 void slist<_Tp,_Alloc>::remove(const _Tp& __val)
793 _Node_base* __cur = &_M_head;
794 while (__cur && __cur->_M_next) {
795 if (((_Node*) __cur->_M_next)->_M_data == __val)
796 _M_erase_after(__cur);
797 else
798 __cur = __cur->_M_next;
802 template <class _Tp, class _Alloc>
803 void slist<_Tp,_Alloc>::unique()
805 _Node_base* __cur = _M_head._M_next;
806 if (__cur) {
807 while (__cur->_M_next) {
808 if (((_Node*)__cur)->_M_data ==
809 ((_Node*)(__cur->_M_next))->_M_data)
810 _M_erase_after(__cur);
811 else
812 __cur = __cur->_M_next;
817 template <class _Tp, class _Alloc>
818 void slist<_Tp,_Alloc>::merge(slist<_Tp,_Alloc>& __x)
820 _Node_base* __n1 = &_M_head;
821 while (__n1->_M_next && __x._M_head._M_next) {
822 if (((_Node*) __x._M_head._M_next)->_M_data <
823 ((_Node*) __n1->_M_next)->_M_data)
824 __slist_splice_after(__n1, &__x._M_head, __x._M_head._M_next);
825 __n1 = __n1->_M_next;
827 if (__x._M_head._M_next) {
828 __n1->_M_next = __x._M_head._M_next;
829 __x._M_head._M_next = 0;
833 template <class _Tp, class _Alloc>
834 void slist<_Tp,_Alloc>::sort()
836 if (_M_head._M_next && _M_head._M_next->_M_next) {
837 slist __carry;
838 slist __counter[64];
839 int __fill = 0;
840 while (!empty()) {
841 __slist_splice_after(&__carry._M_head, &_M_head, _M_head._M_next);
842 int __i = 0;
843 while (__i < __fill && !__counter[__i].empty()) {
844 __counter[__i].merge(__carry);
845 __carry.swap(__counter[__i]);
846 ++__i;
848 __carry.swap(__counter[__i]);
849 if (__i == __fill)
850 ++__fill;
853 for (int __i = 1; __i < __fill; ++__i)
854 __counter[__i].merge(__counter[__i-1]);
855 this->swap(__counter[__fill-1]);
859 #ifdef __STL_MEMBER_TEMPLATES
861 template <class _Tp, class _Alloc>
862 template <class _Predicate>
863 void slist<_Tp,_Alloc>::remove_if(_Predicate __pred)
865 _Node_base* __cur = &_M_head;
866 while (__cur->_M_next) {
867 if (__pred(((_Node*) __cur->_M_next)->_M_data))
868 _M_erase_after(__cur);
869 else
870 __cur = __cur->_M_next;
874 template <class _Tp, class _Alloc> template <class _BinaryPredicate>
875 void slist<_Tp,_Alloc>::unique(_BinaryPredicate __pred)
877 _Node* __cur = (_Node*) _M_head._M_next;
878 if (__cur) {
879 while (__cur->_M_next) {
880 if (__pred(((_Node*)__cur)->_M_data,
881 ((_Node*)(__cur->_M_next))->_M_data))
882 _M_erase_after(__cur);
883 else
884 __cur = (_Node*) __cur->_M_next;
889 template <class _Tp, class _Alloc> template <class _StrictWeakOrdering>
890 void slist<_Tp,_Alloc>::merge(slist<_Tp,_Alloc>& __x,
891 _StrictWeakOrdering __comp)
893 _Node_base* __n1 = &_M_head;
894 while (__n1->_M_next && __x._M_head._M_next) {
895 if (__comp(((_Node*) __x._M_head._M_next)->_M_data,
896 ((_Node*) __n1->_M_next)->_M_data))
897 __slist_splice_after(__n1, &__x._M_head, __x._M_head._M_next);
898 __n1 = __n1->_M_next;
900 if (__x._M_head._M_next) {
901 __n1->_M_next = __x._M_head._M_next;
902 __x._M_head._M_next = 0;
906 template <class _Tp, class _Alloc> template <class _StrictWeakOrdering>
907 void slist<_Tp,_Alloc>::sort(_StrictWeakOrdering __comp)
909 if (_M_head._M_next && _M_head._M_next->_M_next) {
910 slist __carry;
911 slist __counter[64];
912 int __fill = 0;
913 while (!empty()) {
914 __slist_splice_after(&__carry._M_head, &_M_head, _M_head._M_next);
915 int __i = 0;
916 while (__i < __fill && !__counter[__i].empty()) {
917 __counter[__i].merge(__carry, __comp);
918 __carry.swap(__counter[__i]);
919 ++__i;
921 __carry.swap(__counter[__i]);
922 if (__i == __fill)
923 ++__fill;
926 for (int __i = 1; __i < __fill; ++__i)
927 __counter[__i].merge(__counter[__i-1], __comp);
928 this->swap(__counter[__fill-1]);
932 #endif /* __STL_MEMBER_TEMPLATES */
934 #if defined(__sgi) && !defined(__GNUC__) && (_MIPS_SIM != _MIPS_SIM_ABI32)
935 #pragma reset woff 1174
936 #pragma reset woff 1375
937 #endif
939 __STL_END_NAMESPACE
941 #endif /* __SGI_STL_INTERNAL_SLIST_H */
943 // Local Variables:
944 // mode:C++
945 // End: