Commit e135a038 by Benjamin Kosnik

[multiple changes]


2004-01-07  Gawain Bolton  <gp.bolton@computer.org>

	* include/bits/stl_list.h:
	* include/bits/list.tc:
	* src/list.cc:
        Performance enhancements for destructor, push_front(),
        push_back(), pop_front(), pop_back(), sort()
        Eliminated static_casts where possible.
        Moved code out of header files into new src/list.cc
        implementation file for library where possible.
        Remove inheritance from iterator class and create separate
        classes for non-constant and constant iterators.
	* include/bits/stl_tree.h (_Rb_tree class):
	* src/tree.cc:
        Only erase contents in destructor.
        Eliminate unnecessary initialization in assignment operator.
        Optimize for the nominal case by not checking whether
        container is empty in clear().
        Re-order test in _M_insert() to improve performance.
        Move initialization of new node's left & right pointers to
        src/tree.cc to where new node's colour is initialized
        and to reduce the amount of inline code.
        Use  _M_leftmost() and _M_end() to improve readability where
        appropriate.
        Create separate classes for non-constant and constant
        iterators to clarify code, avoid extra template parameters and
        casting away constness.

2004-01-07  Benjamin Kosnik  <bkoz@redhat.com>

	* src/Makefile.am (sources): Add list.cc, tree.cc.
	* src/stl_tree.cc: Move to...
	* src/tree.cc: ...here.
	* src/list.cc: Add.
	* config/linker-map.gnu: Tweaks.
	* testsuite/23_containers/map/operators/1_neg.cc: Add excess errors.
	* testsuite/23_containers/set/operators/1_neg.cc: Add excess errors.

	* bits/stl_vector.h: Column wrap comments.

From-SVN: r75515
parent 85b58ca5
2004-01-07 Gawain Bolton <gp.bolton@computer.org>
* include/bits/stl_list.h:
* include/bits/list.tc:
* src/list.cc:
Performance enhancements for destructor, push_front(),
push_back(), pop_front(), pop_back(), sort()
Eliminated static_casts where possible.
Moved code out of header files into new src/list.cc
implementation file for library where possible.
Remove inheritance from iterator class and create separate
classes for non-constant and constant iterators.
* include/bits/stl_tree.h (_Rb_tree class):
* src/tree.cc:
Only erase contents in destructor.
Eliminate unnecessary initialization in assignment operator.
Optimize for the nominal case by not checking whether
container is empty in clear().
Re-order test in _M_insert() to improve performance.
Move initialization of new node's left & right pointers to
src/tree.cc to where new node's colour is initialized
and to reduce the amount of inline code.
Use _M_leftmost() and _M_end() to improve readability where
appropriate.
Create separate classes for non-constant and constant
iterators to clarify code, avoid extra template parameters and
casting away constness.
2004-01-07 Benjamin Kosnik <bkoz@redhat.com>
* src/Makefile.am (sources): Add list.cc, tree.cc.
* src/stl_tree.cc: Move to...
* src/tree.cc: ...here.
* src/list.cc: Add.
* config/linker-map.gnu: Tweaks.
* testsuite/23_containers/map/operators/1_neg.cc: Add excess errors.
* testsuite/23_containers/set/operators/1_neg.cc: Add excess errors.
* bits/stl_vector.h: Column wrap comments.
2004-01-07 Loren J. Rittle <ljrittle@acm.org>
(re-open) PR libstdc++/12658
......
......@@ -112,13 +112,15 @@ GLIBCXX_3.4 {
_ZSt9has_facet*;
# _Rb_tree
_ZSt18_Rb_tree_decrementPKSt18_Rb_tree_node_base;
_ZSt18_Rb_tree_decrementPSt18_Rb_tree_node_base;
_ZSt18_Rb_tree_incrementPKSt18_Rb_tree_node_base;
_ZSt18_Rb_tree_incrementPSt18_Rb_tree_node_base;
_ZSt18_Rb_tree_rebalancePSt18_Rb_tree_node_baseRS0_;
_ZSt20_Rb_tree_black_countPKSt18_Rb_tree_node_baseS1_;
_ZSt20_Rb_tree_rotate_leftPSt18_Rb_tree_node_baseRS0_;
_ZSt21_Rb_tree_rotate_rightPSt18_Rb_tree_node_baseRS0_;
_ZSt28_Rb_tree_rebalance_for_erasePSt18_Rb_tree_node_baseRS_;
_ZSt29_Rb_tree_insert_and_rebalancebPSt18_Rb_tree_node_baseS0_RS_;
# std::__codecvt_abstract_base*
_ZNStSt23__codecvt_abstract_base*;
......
......@@ -77,45 +77,6 @@ namespace __gnu_norm
std::_Destroy(&__tmp->_M_data);
_M_put_node(__tmp);
}
this->_M_node._M_next = &this->_M_node;
this->_M_node._M_prev = &this->_M_node;
}
template<typename _Tp, typename _Alloc>
void list<_Tp, _Alloc>::
swap(list<_Tp, _Alloc>& __x)
{
if ( this->_M_node._M_next == &this->_M_node )
{
if ( __x._M_node._M_next != &__x._M_node )
{
this->_M_node._M_next = __x._M_node._M_next;
this->_M_node._M_prev = __x._M_node._M_prev;
this->_M_node._M_prev->_M_next = &this->_M_node;
this->_M_node._M_next->_M_prev = this->_M_node._M_prev->_M_next;
__x._M_node._M_next = __x._M_node._M_prev = &__x._M_node;
}
}
else if ( __x._M_node._M_next == &__x._M_node )
{
__x._M_node._M_next = this->_M_node._M_next;
__x._M_node._M_prev = this->_M_node._M_prev;
__x._M_node._M_prev->_M_next = &__x._M_node;
__x._M_node._M_next->_M_prev = __x._M_node._M_prev->_M_next;
this->_M_node._M_next = this->_M_node._M_prev = &this->_M_node;
}
else
{
std::swap(this->_M_node._M_next,__x._M_node._M_next);
std::swap(this->_M_node._M_prev,__x._M_node._M_prev);
this->_M_node._M_prev->_M_next = &this->_M_node;
this->_M_node._M_next->_M_prev = this->_M_node._M_prev->_M_next;
__x._M_node._M_prev->_M_next = &__x._M_node;
__x._M_node._M_next->_M_prev = __x._M_node._M_prev->_M_next;
}
}
template<typename _Tp, typename _Alloc>
......@@ -124,10 +85,7 @@ namespace __gnu_norm
insert(iterator __position, const value_type& __x)
{
_Node* __tmp = _M_create_node(__x);
__tmp->_M_next = __position._M_node;
__tmp->_M_prev = __position._M_node->_M_prev;
__position._M_node->_M_prev->_M_next = __tmp;
__position._M_node->_M_prev = __tmp;
__tmp->hook(__position._M_node);
return __tmp;
}
......@@ -136,14 +94,9 @@ namespace __gnu_norm
list<_Tp,_Alloc>::
erase(iterator __position)
{
_List_node_base* __next_node = __position._M_node->_M_next;
_List_node_base* __prev_node = __position._M_node->_M_prev;
_Node* __n = static_cast<_Node*>(__position._M_node);
__prev_node->_M_next = __next_node;
__next_node->_M_prev = __prev_node;
std::_Destroy(&__n->_M_data);
_M_put_node(__n);
return iterator(static_cast<_Node*>(__next_node));
iterator __ret = __position._M_node->_M_next;
_M_erase(__position);
return __ret;
}
template<typename _Tp, typename _Alloc>
......@@ -226,7 +179,7 @@ namespace __gnu_norm
iterator __next = __first;
++__next;
if (*__first == __value)
erase(__first);
_M_erase(__first);
__first = __next;
}
}
......@@ -243,7 +196,7 @@ namespace __gnu_norm
while (++__next != __last)
{
if (*__first == *__next)
erase(__next);
_M_erase(__next);
else
__first = __next;
__next = __first;
......@@ -277,19 +230,6 @@ namespace __gnu_norm
}
}
// FIXME put this somewhere else
inline void
__List_base_reverse(_List_node_base* __p)
{
_List_node_base* __tmp = __p;
do
{
std::swap(__tmp->_M_next, __tmp->_M_prev);
__tmp = __tmp->_M_prev; // Old next node is now prev.
}
while (__tmp != __p);
}
template<typename _Tp, typename _Alloc>
void
list<_Tp,_Alloc>::
......@@ -300,24 +240,28 @@ namespace __gnu_norm
&& this->_M_node._M_next->_M_next != &this->_M_node)
{
list __carry;
list __counter[64];
int __fill = 0;
while (!empty())
list __tmp[64];
list * __fill = &__tmp[0];
list * __counter;
do
{
__carry.splice(__carry.begin(), *this, begin());
int __i = 0;
while(__i < __fill && !__counter[__i].empty())
for(__counter = &__tmp[0];
(__counter != __fill) && !__counter->empty();
++__counter)
{
__counter[__i].merge(__carry);
__carry.swap(__counter[__i++]);
__counter->merge(__carry);
__carry.swap(*__counter);
}
__carry.swap(__counter[__i]);
if (__i == __fill) ++__fill;
}
for (int __i = 1; __i < __fill; ++__i)
__counter[__i].merge(__counter[__i-1]);
swap(__counter[__fill-1]);
__carry.swap(*__counter);
if (__counter == __fill) ++__fill;
} while ( !empty() );
for (__counter = &__tmp[1]; __counter != __fill; ++__counter)
__counter->merge( *(__counter-1) );
swap( *(__fill-1) );
}
}
......@@ -333,7 +277,7 @@ namespace __gnu_norm
{
iterator __next = __first;
++__next;
if (__pred(*__first)) erase(__first);
if (__pred(*__first)) _M_erase(__first);
__first = __next;
}
}
......@@ -351,7 +295,7 @@ namespace __gnu_norm
while (++__next != __last)
{
if (__binary_pred(*__first, *__next))
erase(__next);
_M_erase(__next);
else
__first = __next;
__next = __first;
......@@ -397,26 +341,31 @@ namespace __gnu_norm
this->_M_node._M_next->_M_next != &this->_M_node)
{
list __carry;
list __counter[64];
int __fill = 0;
while (!empty())
list __tmp[64];
list * __fill = &__tmp[0];
list * __counter;
do
{
__carry.splice(__carry.begin(), *this, begin());
int __i = 0;
while(__i < __fill && !__counter[__i].empty())
for(__counter = &__tmp[0];
(__counter != __fill) && !__counter->empty();
++__counter)
{
__counter[__i].merge(__carry, __comp);
__carry.swap(__counter[__i++]);
__counter->merge(__carry, __comp);
__carry.swap(*__counter);
}
__carry.swap(__counter[__i]);
if (__i == __fill) ++__fill;
}
for (int __i = 1; __i < __fill; ++__i)
__counter[__i].merge(__counter[__i-1], __comp);
swap(__counter[__fill-1]);
__carry.swap(*__counter);
if (__counter == __fill) ++__fill;
} while ( !empty() );
for (__counter = &__tmp[1]; __counter != __fill; ++__counter)
__counter->merge( *(__counter-1), __comp );
swap( *(__fill-1) );
}
}
} // namespace __gnu_norm
#endif /* _LIST_TCC */
......@@ -112,8 +112,8 @@ namespace __gnu_norm
/**
* @brief A standard container which offers fixed time access to individual
* elements in any order.
* @brief A standard container which offers fixed time access to
* individual elements in any order.
*
* @ingroup Containers
* @ingroup Sequences
......@@ -124,10 +124,11 @@ namespace __gnu_norm
* <a href="tables.html#68">optional sequence requirements</a> with the
* %exception of @c push_front and @c pop_front.
*
* In some terminology a %vector can be described as a dynamic C-style array,
* it offers fast and efficient access to individual elements in any order
* and saves the user from worrying about memory and size allocation.
* Subscripting ( @c [] ) access is also provided as with C-style arrays.
* In some terminology a %vector can be described as a dynamic
* C-style array, it offers fast and efficient access to individual
* elements in any order and saves the user from worrying about
* memory and size allocation. Subscripting ( @c [] ) access is
* also provided as with C-style arrays.
*/
template<typename _Tp, typename _Alloc = allocator<_Tp> >
class vector : protected _Vector_base<_Tp, _Alloc>
......@@ -185,7 +186,8 @@ namespace __gnu_norm
vector(size_type __n, const value_type& __value,
const allocator_type& __a = allocator_type())
: _Base(__n, __a)
{ this->_M_finish = std::uninitialized_fill_n(this->_M_start, __n, __value); }
{ this->_M_finish = std::uninitialized_fill_n(this->_M_start,
__n, __value); }
/**
* @brief Create a %vector with default elements.
......@@ -223,11 +225,12 @@ namespace __gnu_norm
* Create a %vector consisting of copies of the elements from
* [first,last).
*
* If the iterators are forward, bidirectional, or random-access, then
* this will call the elements' copy constructor N times (where N is
* distance(first,last)) and do no memory reallocation. But if only
* input iterators are used, then this will do at most 2N calls to the
* copy constructor, and logN memory reallocations.
* If the iterators are forward, bidirectional, or
* random-access, then this will call the elements' copy
* constructor N times (where N is distance(first,last)) and do
* no memory reallocation. But if only input iterators are
* used, then this will do at most 2N calls to the copy
* constructor, and logN memory reallocations.
*/
template<typename _InputIterator>
vector(_InputIterator __first, _InputIterator __last,
......@@ -240,9 +243,10 @@ namespace __gnu_norm
}
/**
* The dtor only erases the elements, and note that if the elements
* themselves are pointers, the pointed-to memory is not touched in any
* way. Managing the pointer is the user's responsibilty.
* The dtor only erases the elements, and note that if the
* elements themselves are pointers, the pointed-to memory is
* not touched in any way. Managing the pointer is the user's
* responsibilty.
*/
~vector() { std::_Destroy(this->_M_start, this->_M_finish); }
......@@ -297,8 +301,9 @@ namespace __gnu_norm
// iterators
/**
* Returns a read/write iterator that points to the first element in the
* %vector. Iteration is done in ordinary element order.
* Returns a read/write iterator that points to the first
* element in the %vector. Iteration is done in ordinary
* element order.
*/
iterator
begin() { return iterator (this->_M_start); }
......@@ -320,8 +325,9 @@ namespace __gnu_norm
end() { return iterator (this->_M_finish); }
/**
* Returns a read-only (constant) iterator that points one past the last
* element in the %vector. Iteration is done in ordinary element order.
* Returns a read-only (constant) iterator that points one past
* the last element in the %vector. Iteration is done in
* ordinary element order.
*/
const_iterator
end() const { return const_iterator (this->_M_finish); }
......@@ -343,9 +349,9 @@ namespace __gnu_norm
rbegin() const { return const_reverse_iterator(end()); }
/**
* Returns a read/write reverse iterator that points to one before the
* first element in the %vector. Iteration is done in reverse element
* order.
* Returns a read/write reverse iterator that points to one
* before the first element in the %vector. Iteration is done
* in reverse element order.
*/
reverse_iterator
rend() { return reverse_iterator(begin()); }
......@@ -401,8 +407,8 @@ namespace __gnu_norm
resize(size_type __new_size) { resize(__new_size, value_type()); }
/**
* Returns the total number of elements that the %vector can hold before
* needing to allocate more memory.
* Returns the total number of elements that the %vector can
* hold before needing to allocate more memory.
*/
size_type
capacity() const
......@@ -438,7 +444,8 @@ namespace __gnu_norm
// element access
/**
* @brief Subscript access to the data contained in the %vector.
* @param n The index of the element for which data should be accessed.
* @param n The index of the element for which data should be
* accessed.
* @return Read/write reference to data.
*
* This operator allows for easy, array-style, data access.
......@@ -480,9 +487,9 @@ namespace __gnu_norm
* @return Read/write reference to data.
* @throw std::out_of_range If @a n is an invalid index.
*
* This function provides for safer data access. The parameter is first
* checked that it is in the range of the vector. The function throws
* out_of_range if the check fails.
* This function provides for safer data access. The parameter
* is first checked that it is in the range of the vector. The
* function throws out_of_range if the check fails.
*/
reference
at(size_type __n) { _M_range_check(__n); return (*this)[__n]; }
......@@ -516,15 +523,15 @@ namespace __gnu_norm
front() const { return *begin(); }
/**
* Returns a read/write reference to the data at the last element of the
* %vector.
* Returns a read/write reference to the data at the last
* element of the %vector.
*/
reference
back() { return *(end() - 1); }
/**
* Returns a read-only (constant) reference to the data at the last
* element of the %vector.
* Returns a read-only (constant) reference to the data at the
* last element of the %vector.
*/
const_reference
back() const { return *(end() - 1); }
......@@ -557,8 +564,9 @@ namespace __gnu_norm
*
* This is a typical stack operation. It shrinks the %vector by one.
*
* Note that no data is returned, and if the last element's data is
* needed, it should be retrieved before pop_back() is called.
* Note that no data is returned, and if the last element's
* data is needed, it should be retrieved before pop_back() is
* called.
*/
void
pop_back()
......@@ -614,7 +622,8 @@ namespace __gnu_norm
*/
template<typename _InputIterator>
void
insert(iterator __position, _InputIterator __first, _InputIterator __last)
insert(iterator __position, _InputIterator __first,
_InputIterator __last)
{
// Check whether it's an integral type. If so, it's not an iterator.
typedef typename _Is_integer<_InputIterator>::_Integral _Integral;
......@@ -721,7 +730,8 @@ namespace __gnu_norm
{
this->_M_start = _M_allocate(__n);
this->_M_end_of_storage = this->_M_start + __n;
this->_M_finish = std::uninitialized_fill_n(this->_M_start, __n, __value);
this->_M_finish = std::uninitialized_fill_n(this->_M_start,
__n, __value);
}
// Called by the range constructor to implement [23.1.1]/9
......@@ -774,7 +784,8 @@ namespace __gnu_norm
// Called by the range assign to implement [23.1.1]/9
template<typename _InputIterator>
void
_M_assign_dispatch(_InputIterator __first, _InputIterator __last, __false_type)
_M_assign_dispatch(_InputIterator __first, _InputIterator __last,
__false_type)
{
typedef typename iterator_traits<_InputIterator>::iterator_category
_IterCategory;
......
......@@ -104,13 +104,14 @@ sources = \
ios_init.cc \
ios_locale.cc \
limits.cc \
list.cc \
locale.cc \
locale_init.cc \
locale_facets.cc \
localename.cc \
stdexcept.cc \
stl_tree.cc \
strstream.cc \
tree.cc \
allocator-inst.cc \
concept-inst.cc \
fstream-inst.cc \
......
......@@ -260,13 +260,14 @@ sources = \
ios_init.cc \
ios_locale.cc \
limits.cc \
list.cc \
locale.cc \
locale_init.cc \
locale_facets.cc \
localename.cc \
stdexcept.cc \
stl_tree.cc \
strstream.cc \
tree.cc \
allocator-inst.cc \
concept-inst.cc \
fstream-inst.cc \
......@@ -361,13 +362,13 @@ am__objects_1 = codecvt_members.lo collate_members.lo ctype_members.lo \
am__objects_2 = basic_file.lo c++locale.lo
am__objects_3 = codecvt.lo complex_io.lo ctype.lo debug.lo demangle.lo \
functexcept.lo globals_locale.lo globals_io.lo ios.lo \
ios_failure.lo ios_init.lo ios_locale.lo limits.lo locale.lo \
locale_init.lo locale_facets.lo localename.lo stdexcept.lo \
stl_tree.lo strstream.lo allocator-inst.lo concept-inst.lo \
fstream-inst.lo ext-inst.lo io-inst.lo istream-inst.lo \
locale-inst.lo locale-misc-inst.lo misc-inst.lo ostream-inst.lo \
sstream-inst.lo streambuf-inst.lo string-inst.lo \
valarray-inst.lo wlocale-inst.lo wstring-inst.lo \
ios_failure.lo ios_init.lo ios_locale.lo limits.lo list.lo \
locale.lo locale_init.lo locale_facets.lo localename.lo \
stdexcept.lo strstream.lo tree.lo allocator-inst.lo \
concept-inst.lo fstream-inst.lo ext-inst.lo io-inst.lo \
istream-inst.lo locale-inst.lo locale-misc-inst.lo misc-inst.lo \
ostream-inst.lo sstream-inst.lo streambuf-inst.lo \
string-inst.lo valarray-inst.lo wlocale-inst.lo wstring-inst.lo \
$(am__objects_1) $(am__objects_2)
am_libstdc___la_OBJECTS = $(am__objects_3)
libstdc___la_OBJECTS = $(am_libstdc___la_OBJECTS)
......
// std::list utilities implementation -*- C++ -*-
// Copyright (C) 2003 Free Software Foundation, Inc.
//
// This file is part of the GNU ISO C++ Library. This library is free
// software; you can redistribute it and/or modify it under the
// terms of the GNU General Public License as published by the
// Free Software Foundation; either version 2, or (at your option)
// any later version.
// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
// You should have received a copy of the GNU General Public License along
// with this library; see the file COPYING. If not, write to the Free
// Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
// USA.
// As a special exception, you may use this file as part of a free software
// library without restriction. Specifically, if other files instantiate
// templates or use macros or inline functions from this file, or you compile
// this file and link it with other files to produce an executable, this
// file does not by itself cause the resulting executable to be covered by
// the GNU General Public License. This exception does not however
// invalidate any other reasons why the executable file might be covered by
// the GNU General Public License.
/*
*
* 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) 1996,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.
*/
#include <list>
namespace __gnu_norm
{
void
_List_node_base::swap(_List_node_base& __x, _List_node_base& __y)
{
if ( __x._M_next != &__x )
{
if ( __y._M_next != &__y )
{
// Both __x and __y are not empty.
std::swap(__x._M_next,__y._M_next);
std::swap(__x._M_prev,__y._M_prev);
__x._M_next->_M_prev = __x._M_prev->_M_next = &__x;
__y._M_next->_M_prev = __y._M_prev->_M_next = &__y;
}
else
{
// __x is not empty, __y is empty.
__y._M_next = __x._M_next;
__y._M_prev = __x._M_prev;
__y._M_next->_M_prev = __y._M_prev->_M_next = &__y;
__x._M_next = __x._M_prev = &__x;
}
}
else if ( __y._M_next != &__y )
{
// __x is empty, __y is not empty.
__x._M_next = __y._M_next;
__x._M_prev = __y._M_prev;
__x._M_next->_M_prev = __x._M_prev->_M_next = &__x;
__y._M_next = __y._M_prev = &__y;
}
}
void
_List_node_base::transfer(_List_node_base * const __first,
_List_node_base * const __last)
{
if (this != __last)
{
// Remove [first, last) from its old position.
__last->_M_prev->_M_next = this;
__first->_M_prev->_M_next = __last;
this->_M_prev->_M_next = __first;
// Splice [first, last) into its new position.
_List_node_base* const __tmp = this->_M_prev;
this->_M_prev = __last->_M_prev;
__last->_M_prev = __first->_M_prev;
__first->_M_prev = __tmp;
}
}
void
_List_node_base::reverse()
{
_List_node_base* __tmp = this;
do
{
std::swap(__tmp->_M_next, __tmp->_M_prev);
__tmp = __tmp->_M_prev; // Old next node is now prev.
}
while (__tmp != this);
}
void
_List_node_base::hook(_List_node_base * const __position)
{
this->_M_next = __position;
this->_M_prev = __position->_M_prev;
__position->_M_prev->_M_next = this;
__position->_M_prev = this;
}
void
_List_node_base::unhook()
{
_List_node_base* const __next_node = this->_M_next;
_List_node_base* const __prev_node = this->_M_prev;
__prev_node->_M_next = __next_node;
__next_node->_M_prev = __prev_node;
}
} // namespace __gnu_norm
......@@ -82,6 +82,12 @@ namespace std
return __x;
}
const _Rb_tree_node_base*
_Rb_tree_increment(const _Rb_tree_node_base* __x)
{
return _Rb_tree_increment(const_cast<_Rb_tree_node_base*>(__x));
}
_Rb_tree_node_base*
_Rb_tree_decrement(_Rb_tree_node_base* __x)
{
......@@ -108,6 +114,12 @@ namespace std
return __x;
}
const _Rb_tree_node_base*
_Rb_tree_decrement(const _Rb_tree_node_base* __x)
{
return _Rb_tree_decrement(const_cast<_Rb_tree_node_base*>(__x));
}
void
_Rb_tree_rotate_left(_Rb_tree_node_base* const __x,
_Rb_tree_node_base*& __root)
......@@ -151,10 +163,43 @@ namespace std
}
void
_Rb_tree_rebalance(_Rb_tree_node_base* __x, _Rb_tree_node_base*& __root)
_Rb_tree_insert_and_rebalance(const bool __insert_left,
_Rb_tree_node_base* __x,
_Rb_tree_node_base* __p,
_Rb_tree_node_base& __header)
{
_Rb_tree_node_base *& __root = __header._M_parent;
// Initialize fields in new node to insert.
__x->_M_parent = __p;
__x->_M_left = 0;
__x->_M_right = 0;
__x->_M_color = _S_red;
// Insert.
// Make new node child of parent and maintain root, leftmost and
// rightmost nodes.
// N.B. First node is always inserted left.
if (__insert_left)
{
__p->_M_left = __x; // also makes leftmost = __x when __p == &__header
if (__p == &__header)
{
__header._M_parent = __x;
__header._M_right = __x;
}
else if (__p == __header._M_left)
__header._M_left = __x; // maintain leftmost pointing to min node
}
else
{
__p->_M_right = __x;
if (__p == __header._M_right)
__header._M_right = __x; // maintain rightmost pointing to max node
}
// Rebalance.
while (__x != __root
&& __x->_M_parent->_M_color == _S_red)
{
......
// 2000-09-07 bgarcia@laurelnetworks.com
// { dg-do compile }
// Copyright (C) 2000, 2001, 2002 Free Software Foundation, Inc.
// Copyright (C) 2000, 2001, 2002, 2004 Free Software Foundation, Inc.
//
// This file is part of the GNU ISO C++ Library. This library is free
// software; you can redistribute it and/or modify it under the
......@@ -19,12 +19,11 @@
// USA.
// 23.3.4 template class multiset negative tests
// 2000-09-07 bgarcia@laurelnetworks.com
#include <map>
#include <string>
// { dg-do compile }
// libstdc++/86: map & set iterator comparisons are not type-safe
void test01()
{
......@@ -42,8 +41,5 @@ void test01()
test &= itr == mapByName.end(); // { dg-error "no" }
}
int main()
{
test01();
return 0;
}
// { dg-error "candidates are" "" { target *-*-* } 212 }
// { dg-error "candidates are" "" { target *-*-* } 216 }
// 2000-09-07 bgarcia@laurelnetworks.com
// { dg-do compile }
// Copyright (C) 2000, 2001, 2002 Free Software Foundation, Inc.
// Copyright (C) 2000, 2001, 2002, 2004 Free Software Foundation, Inc.
//
// This file is part of the GNU ISO C++ Library. This library is free
// software; you can redistribute it and/or modify it under the
......@@ -19,14 +19,13 @@
// USA.
// 23.3.4 template class multiset negative tests
// 2000-09-07 bgarcia@laurelnetworks.com
#include <set>
#include <string>
// { dg-do compile }
// libstdc++/86: map & set iterator comparisons are not type-safe
int main(void)
void test01()
{
bool test __attribute__((unused)) = true;
......@@ -38,6 +37,7 @@ int main(void)
// NB: it's not setByIndex!!
test &= itr != setByName.end(); // { dg-error "no" }
test &= itr == setByName.end(); // { dg-error "no" }
return 0;
}
// { dg-error "candidates are" "" { target *-*-* } 285 }
// { dg-error "candidates are" "" { target *-*-* } 289 }
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment