mirror of
https://github.com/panda3d/panda3d.git
synced 2025-10-03 18:31:55 -04:00
improvements to ordered_vector
This commit is contained in:
parent
b20474cb50
commit
f81078dd29
@ -17,6 +17,31 @@
|
|||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ordered_vector::EquivalentTest::Constructor
|
||||||
|
// Access: Public
|
||||||
|
// Description:
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE ordered_vector<Key, Compare>::EquivalentTest::
|
||||||
|
EquivalentTest(const Compare &compare) :
|
||||||
|
_compare(compare)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ordered_vector::EquivalentTest::operator ()
|
||||||
|
// Access: Public
|
||||||
|
// Description:
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE bool ordered_vector<Key, Compare>::EquivalentTest::
|
||||||
|
operator () (const ordered_vector<Key, Compare>::key_type &a,
|
||||||
|
const ordered_vector<Key, Compare>::key_type &b) {
|
||||||
|
nassertr(!_compare(b, a), false);
|
||||||
|
return !_compare(a, b);
|
||||||
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
// Function: ordered_vector::Constructor
|
// Function: ordered_vector::Constructor
|
||||||
// Access: Public
|
// Access: Public
|
||||||
@ -161,6 +186,28 @@ rend() const {
|
|||||||
return _vector.rend();
|
return _vector.rend();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ordered_vector::operator []
|
||||||
|
// Access: Public
|
||||||
|
// Description: Returns the nth element.
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE ordered_vector<Key, Compare>::reference ordered_vector<Key, Compare>::
|
||||||
|
operator [] (ordered_vector<Key, Compare>::size_type n) {
|
||||||
|
return _vector[n];
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ordered_vector::operator []
|
||||||
|
// Access: Public
|
||||||
|
// Description: Returns the nth element.
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE ordered_vector<Key, Compare>::const_reference ordered_vector<Key, Compare>::
|
||||||
|
operator [] (ordered_vector<Key, Compare>::size_type n) const {
|
||||||
|
return _vector[n];
|
||||||
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
// Function: ordered_vector::size
|
// Function: ordered_vector::size
|
||||||
// Access: Public
|
// Access: Public
|
||||||
@ -274,17 +321,54 @@ operator >= (const ordered_vector<Key, Compare> &other) const {
|
|||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
// Function: ordered_vector::insert
|
// Function: ordered_vector::insert_unique
|
||||||
|
// Access: Public
|
||||||
|
// Description: Inserts the indicated key into the ordered vector, at
|
||||||
|
// the appropriate place. If there is already an element
|
||||||
|
// sorting equivalent to the key in the vector, the new
|
||||||
|
// key is not inserted.
|
||||||
|
//
|
||||||
|
// The return value is a pair, where the first component
|
||||||
|
// is the iterator referencing the new element (or the
|
||||||
|
// original element), and the second componet is true if
|
||||||
|
// the insert operation has taken place.
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE pair<ordered_vector<Key, Compare>::iterator, bool> ordered_vector<Key, Compare>::
|
||||||
|
insert_unique(const ordered_vector<Key, Compare>::value_type &key) {
|
||||||
|
iterator position = find_insert_position(begin(), end(), key);
|
||||||
|
#ifdef NDEBUG
|
||||||
|
pair<iterator, bool> bogus_result(end(), false);
|
||||||
|
nassertr(position >= begin() && position <= end(), bogus_result);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// If there's already an equivalent key in the vector, it's at
|
||||||
|
// *(position - 1).
|
||||||
|
if (position != begin() && !_compare(*(position - 1), key)) {
|
||||||
|
pair<iterator, bool> result(position - 1, false);
|
||||||
|
nassertr(!_compare(key, *(position - 1)), result);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
iterator result = _vector.insert(position, key);
|
||||||
|
verify_list();
|
||||||
|
return pair<iterator, bool>(result, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ordered_vector::insert_nonunique
|
||||||
// Access: Public
|
// Access: Public
|
||||||
// Description: Inserts the indicated key into the ordered vector, at
|
// Description: Inserts the indicated key into the ordered vector, at
|
||||||
// the appropriate place. If there are already elements
|
// the appropriate place. If there are already elements
|
||||||
// sorting equivalent to the key in the vector, the new
|
// sorting equivalent to the key in the vector, the new
|
||||||
// value is inserted following them. The return value
|
// value is inserted following them.
|
||||||
// is the iterator referencing the new element.
|
|
||||||
|
// The return value is the iterator referencing the new
|
||||||
|
// element.
|
||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
template<class Key, class Compare>
|
template<class Key, class Compare>
|
||||||
INLINE ordered_vector<Key, Compare>::iterator ordered_vector<Key, Compare>::
|
INLINE ordered_vector<Key, Compare>::iterator ordered_vector<Key, Compare>::
|
||||||
insert(const ordered_vector<Key, Compare>::value_type &key) {
|
insert_nonunique(const ordered_vector<Key, Compare>::value_type &key) {
|
||||||
iterator position = find_insert_position(begin(), end(), key);
|
iterator position = find_insert_position(begin(), end(), key);
|
||||||
nassertr(position >= begin() && position <= end(), end());
|
nassertr(position >= begin() && position <= end(), end());
|
||||||
|
|
||||||
@ -528,17 +612,52 @@ reserve(ordered_vector<Key, Compare>::size_type n) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
// Function: ordered_vector::sort
|
// Function: ordered_vector::sort_unique
|
||||||
// Access: Public
|
// Access: Public
|
||||||
// Description: Ensures that the vector is properly sorted after a
|
// Description: Ensures that the vector is properly sorted after a
|
||||||
// potentially damaging operation. This should not
|
// potentially damaging operation. This should not
|
||||||
// normally need to be called, unless the user has
|
// normally need to be called, unless the user has
|
||||||
// written to the vector using the non-const iterators.
|
// written to the vector using the non-const iterators
|
||||||
|
// or has called push_back().
|
||||||
|
//
|
||||||
|
// This flavor of sort also eliminates repeated
|
||||||
|
// elements.
|
||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
template<class Key, class Compare>
|
template<class Key, class Compare>
|
||||||
INLINE void ordered_vector<Key, Compare>::
|
INLINE void ordered_vector<Key, Compare>::
|
||||||
sort() {
|
sort_unique() {
|
||||||
::sort(begin(), end(), _compare);
|
sort(begin(), end(), _compare);
|
||||||
|
iterator new_end = unique(begin(), end(), EquivalentTest(_compare));
|
||||||
|
erase(new_end, end());
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ordered_vector::sort_nonunique
|
||||||
|
// Access: Public
|
||||||
|
// Description: Ensures that the vector is properly sorted after a
|
||||||
|
// potentially damaging operation. This should not
|
||||||
|
// normally need to be called, unless the user has
|
||||||
|
// written to the vector using the non-const iterators
|
||||||
|
// or has called push_back().
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE void ordered_vector<Key, Compare>::
|
||||||
|
sort_nonunique() {
|
||||||
|
sort(begin(), end(), _compare);
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ordered_vector::push_back
|
||||||
|
// Access: Public
|
||||||
|
// Description: Adds the new element to the end of the vector without
|
||||||
|
// regard for proper sorting. This is a bad idea to do
|
||||||
|
// except to populate the vector the first time; be sure
|
||||||
|
// to call sort() after you have added all the elements.
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE void ordered_vector<Key, Compare>::
|
||||||
|
push_back(const value_type &key) {
|
||||||
|
_vector.push_back(key);
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
@ -606,3 +725,143 @@ verify_list() {
|
|||||||
#endif
|
#endif
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_set::Constructor
|
||||||
|
// Access: Public
|
||||||
|
// Description:
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE ov_set<Key, Compare>::
|
||||||
|
ov_set(const Compare &compare) :
|
||||||
|
ordered_vector(compare)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_set::Copy Constructor
|
||||||
|
// Access: Public
|
||||||
|
// Description:
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE ov_set<Key, Compare>::
|
||||||
|
ov_set(const ov_set<Key, Compare> ©) :
|
||||||
|
ordered_vector(copy)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_set::Copy Assignment Operator
|
||||||
|
// Access: Public
|
||||||
|
// Description:
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE ov_set<Key, Compare> &ov_set<Key, Compare>::
|
||||||
|
operator = (const ov_set<Key, Compare> ©) {
|
||||||
|
ordered_vector::operator = (copy);
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_set::insert
|
||||||
|
// Access: Public
|
||||||
|
// Description: Maps to insert_unique().
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
ov_set<Key, Compare>::iterator ov_set<Key, Compare>::
|
||||||
|
insert(ordered_vector<Key, Compare>::iterator position,
|
||||||
|
const ordered_vector<Key, Compare>::value_type &key) {
|
||||||
|
return ordered_vector::insert_unique(position, key);
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_set::insert
|
||||||
|
// Access: Public
|
||||||
|
// Description: Maps to insert_unique().
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE pair<ov_set<Key, Compare>::iterator, bool> ov_set<Key, Compare>::
|
||||||
|
insert(const ordered_vector<Key, Compare>::value_type &key) {
|
||||||
|
return ordered_vector::insert_unique(key);
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_set::sort
|
||||||
|
// Access: Public
|
||||||
|
// Description: Maps to sort_unique().
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE void ov_set<Key, Compare>::
|
||||||
|
sort() {
|
||||||
|
return ordered_vector::sort_unique();
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_multiset::Constructor
|
||||||
|
// Access: Public
|
||||||
|
// Description:
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE ov_multiset<Key, Compare>::
|
||||||
|
ov_multiset(const Compare &compare) :
|
||||||
|
ordered_vector(compare)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_multiset::Copy Constructor
|
||||||
|
// Access: Public
|
||||||
|
// Description:
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE ov_multiset<Key, Compare>::
|
||||||
|
ov_multiset(const ov_multiset<Key, Compare> ©) :
|
||||||
|
ordered_vector(copy)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_multiset::Copy Assignment Operator
|
||||||
|
// Access: Public
|
||||||
|
// Description:
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE ov_multiset<Key, Compare> &ov_multiset<Key, Compare>::
|
||||||
|
operator = (const ov_multiset<Key, Compare> ©) {
|
||||||
|
ordered_vector::operator = (copy);
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_multiset::insert
|
||||||
|
// Access: Public
|
||||||
|
// Description: Maps to insert_nonunique().
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
ov_multiset<Key, Compare>::iterator ov_multiset<Key, Compare>::
|
||||||
|
insert(ordered_vector<Key, Compare>::iterator position,
|
||||||
|
const ordered_vector<Key, Compare>::value_type &key) {
|
||||||
|
return ordered_vector::insert_nonunique(position, key);
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_multiset::insert
|
||||||
|
// Access: Public
|
||||||
|
// Description: Maps to insert_nonunique().
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE pair<ov_multiset<Key, Compare>::iterator, bool> ov_multiset<Key, Compare>::
|
||||||
|
insert(const ordered_vector<Key, Compare>::value_type &key) {
|
||||||
|
return ordered_vector::insert_nonunique(key);
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ov_multiset::sort
|
||||||
|
// Access: Public
|
||||||
|
// Description: Maps to sort_nonunique().
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
INLINE void ov_multiset<Key, Compare>::
|
||||||
|
sort() {
|
||||||
|
return ordered_vector::sort_nonunique();
|
||||||
|
}
|
||||||
|
@ -18,31 +18,83 @@
|
|||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
// Function: ordered_vector::insert
|
// Function: ordered_vector::insert_unique
|
||||||
// Access: Public
|
// Access: Public
|
||||||
// Description: Inserts the indicated key into the ordered vector.
|
// Description: Inserts the indicated key into the ordered vector.
|
||||||
// The iterator is a hint to the expected position; if
|
// The iterator is a hint to the expected position; if
|
||||||
// this is correct, the insert operation is likely to be
|
// this is correct, the insert operation is likely to be
|
||||||
// faster. The return value is the iterator referencing
|
// faster. The return value is the iterator referencing
|
||||||
// the new element.
|
// the new element.
|
||||||
|
//
|
||||||
|
// This flavor of insert does not allow multiple copies
|
||||||
|
// of the same key to be inserted. If the key is
|
||||||
|
// already present, it is not inserted, and the iterator
|
||||||
|
// referencing the original value is returned.
|
||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
template<class Key, class Compare>
|
template<class Key, class Compare>
|
||||||
ordered_vector<Key, Compare>::iterator ordered_vector<Key, Compare>::
|
ordered_vector<Key, Compare>::iterator ordered_vector<Key, Compare>::
|
||||||
insert(ordered_vector<Key, Compare>::iterator position,
|
insert_unique(ordered_vector<Key, Compare>::iterator position,
|
||||||
const ordered_vector<Key, Compare>::value_type &key) {
|
const ordered_vector<Key, Compare>::value_type &key) {
|
||||||
|
if (position != end()) {
|
||||||
|
// If we're not inserting at the end, the element we're
|
||||||
|
// inserting before should not lexicographically precede this one.
|
||||||
|
if (_compare(*position, key)) {
|
||||||
|
return insert_unique(key).first;
|
||||||
|
|
||||||
|
} else if (!_compare(key, *position)) {
|
||||||
|
// Oops, !(*position < key) and !(key < *position). That means
|
||||||
|
// they're equivalent, and we shouldn't insert a new one.
|
||||||
|
return position;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (position != begin()) {
|
if (position != begin()) {
|
||||||
// If we're not inserting at the beginning, this element should
|
// If we're not inserting at the beginning, this element should
|
||||||
// not lexicographically precede the one we're inserting after.
|
// not lexicographically precede the one we're inserting after.
|
||||||
if (_compare(key, *(position - 1))) {
|
if (_compare(key, *(position - 1))) {
|
||||||
return insert(key);
|
return insert_unique(key).first;
|
||||||
|
|
||||||
|
} else if (!_compare(*(position - 1), key)) {
|
||||||
|
// Once again, they're equivalent.
|
||||||
|
return position - 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Otherwise, we may insert where the caller requested.
|
||||||
|
iterator result = _vector.insert(position, key);
|
||||||
|
verify_list();
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Function: ordered_vector::insert_nonunique
|
||||||
|
// Access: Public
|
||||||
|
// Description: Inserts the indicated key into the ordered vector.
|
||||||
|
// The iterator is a hint to the expected position; if
|
||||||
|
// this is correct, the insert operation is likely to be
|
||||||
|
// faster. The return value is the iterator referencing
|
||||||
|
// the new element.
|
||||||
|
//
|
||||||
|
// This flavor of insert allows multiple copies of the
|
||||||
|
// same key to be inserted.
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare>
|
||||||
|
ordered_vector<Key, Compare>::iterator ordered_vector<Key, Compare>::
|
||||||
|
insert_nonunique(ordered_vector<Key, Compare>::iterator position,
|
||||||
|
const ordered_vector<Key, Compare>::value_type &key) {
|
||||||
if (position != end()) {
|
if (position != end()) {
|
||||||
// If we're not inserting at the beginning, the element we're
|
// If we're not inserting at the end, the element we're
|
||||||
// inserting before should not lexicographically precede this one.
|
// inserting before should not lexicographically precede this one.
|
||||||
if (_compare(*position, key)) {
|
if (_compare(*position, key)) {
|
||||||
return insert(key);
|
return insert_nonunique(key);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (position != begin()) {
|
||||||
|
// If we're not inserting at the beginning, this element should
|
||||||
|
// not lexicographically precede the one we're inserting after.
|
||||||
|
if (_compare(key, *(position - 1))) {
|
||||||
|
return insert_nonunique(key);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -29,13 +29,38 @@
|
|||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
// Class : ordered_vector
|
// Class : ordered_vector
|
||||||
// Description : This template class presents an interface similar to
|
// Description : This template class presents an interface similar to
|
||||||
// the STL multiset, but it is implemented using a vector
|
// the STL set or multiset (and ov_set and ov_multiset
|
||||||
// that is kept always in sorted order.
|
// are implemented specifically, below), but it is
|
||||||
|
// implemented using a vector that is kept always in
|
||||||
|
// sorted order.
|
||||||
//
|
//
|
||||||
// This allows the ordered_vector to maintain stability
|
// In most cases, an ov_set or ov_multiset may be
|
||||||
// of order between elements that sort equally: they are
|
// dropped in transparently in place of a set or
|
||||||
// stored in the order in which they were added, from
|
// multiset, but the implementation difference has a few
|
||||||
// back to front.
|
// implications:
|
||||||
|
//
|
||||||
|
// (1) The ov_multiset will maintain stability of order
|
||||||
|
// between elements that sort equally: they are stored
|
||||||
|
// in the order in which they were added, from back to
|
||||||
|
// front.
|
||||||
|
//
|
||||||
|
// (2) Insert and erase operations into the middle of
|
||||||
|
// the set can be slow, just as inserting into the
|
||||||
|
// middle of a vector can be slow. In fact, building up
|
||||||
|
// an ov_set by inserting elements one at a time is an
|
||||||
|
// n^2 operation. On the other hand, building up an
|
||||||
|
// ov_set by adding elements to the end, one at time, is
|
||||||
|
// somewhat faster than building up a traditional set;
|
||||||
|
// and you can even add unsorted elements with
|
||||||
|
// push_back() and then call sort() when you're done,
|
||||||
|
// for a log(n) operation.
|
||||||
|
//
|
||||||
|
// (3) Iterators may not be valid for the life of the
|
||||||
|
// ordered_vector. If the vector reallocates itself,
|
||||||
|
// all iterators are invalidated.
|
||||||
|
//
|
||||||
|
// (4) Random access into the set is easy with the []
|
||||||
|
// operator.
|
||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
template<class Key, class Compare = less<Key> >
|
template<class Key, class Compare = less<Key> >
|
||||||
class ordered_vector {
|
class ordered_vector {
|
||||||
@ -81,6 +106,10 @@ public:
|
|||||||
INLINE const_reverse_iterator rbegin() const;
|
INLINE const_reverse_iterator rbegin() const;
|
||||||
INLINE const_reverse_iterator rend() const;
|
INLINE const_reverse_iterator rend() const;
|
||||||
|
|
||||||
|
// Random access.
|
||||||
|
INLINE reference operator [] (size_type n);
|
||||||
|
INLINE const_reference operator [] (size_type n) const;
|
||||||
|
|
||||||
// Size information.
|
// Size information.
|
||||||
INLINE size_type size() const;
|
INLINE size_type size() const;
|
||||||
INLINE size_type max_size() const;
|
INLINE size_type max_size() const;
|
||||||
@ -96,8 +125,10 @@ public:
|
|||||||
INLINE bool operator >= (const ordered_vector<Key, Compare> &other) const;
|
INLINE bool operator >= (const ordered_vector<Key, Compare> &other) const;
|
||||||
|
|
||||||
// Insert operations.
|
// Insert operations.
|
||||||
iterator insert(iterator position, const value_type &key);
|
iterator insert_unique(iterator position, const value_type &key);
|
||||||
INLINE iterator insert(const value_type &key);
|
iterator insert_nonunique(iterator position, const value_type &key);
|
||||||
|
INLINE pair<iterator, bool> insert_unique(const value_type &key);
|
||||||
|
INLINE iterator insert_nonunique(const value_type &key);
|
||||||
|
|
||||||
// Erase operations.
|
// Erase operations.
|
||||||
INLINE iterator erase(iterator position);
|
INLINE iterator erase(iterator position);
|
||||||
@ -122,7 +153,10 @@ public:
|
|||||||
// Special operations.
|
// Special operations.
|
||||||
INLINE void swap(ordered_vector<Key, Compare> &other);
|
INLINE void swap(ordered_vector<Key, Compare> &other);
|
||||||
INLINE void reserve(size_type n);
|
INLINE void reserve(size_type n);
|
||||||
INLINE void sort();
|
INLINE void sort_unique();
|
||||||
|
INLINE void sort_nonunique();
|
||||||
|
|
||||||
|
INLINE void push_back(const value_type &key);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
INLINE iterator nci(const_iterator iterator);
|
INLINE iterator nci(const_iterator iterator);
|
||||||
@ -151,10 +185,57 @@ private:
|
|||||||
bool verify_list_impl(iterator first, iterator last);
|
bool verify_list_impl(iterator first, iterator last);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
// This function object is used in sort_unique(). It returns true
|
||||||
|
// if two consecutive sorted elements are equivalent.
|
||||||
|
class EquivalentTest {
|
||||||
|
public:
|
||||||
|
INLINE EquivalentTest(const Compare &compare);
|
||||||
|
INLINE bool operator () (const key_type &a, const key_type &b);
|
||||||
|
Compare _compare;
|
||||||
|
};
|
||||||
|
|
||||||
Compare _compare;
|
Compare _compare;
|
||||||
Vector _vector;
|
Vector _vector;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Class : ov_set
|
||||||
|
// Description : A specialization of ordered_vector that emulates a
|
||||||
|
// standard STL set: one copy of each element is
|
||||||
|
// allowed.
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare = less<Key> >
|
||||||
|
class ov_set : public ordered_vector<Key, Compare> {
|
||||||
|
public:
|
||||||
|
INLINE ov_set(const Compare &compare = Compare());
|
||||||
|
INLINE ov_set(const ov_set<Key, Compare> ©);
|
||||||
|
INLINE ov_set<Key, Compare> &operator = (const ov_set<Key, Compare> ©);
|
||||||
|
|
||||||
|
INLINE iterator insert(iterator position, const value_type &key);
|
||||||
|
INLINE pair<iterator, bool> insert(const value_type &key);
|
||||||
|
|
||||||
|
INLINE void sort();
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
// Class : ov_multiset
|
||||||
|
// Description : A specialization of ordered_vector that emulates a
|
||||||
|
// standard STL set: many copies of each element are
|
||||||
|
// allowed.
|
||||||
|
////////////////////////////////////////////////////////////////////
|
||||||
|
template<class Key, class Compare = less<Key> >
|
||||||
|
class ov_multiset : public ordered_vector<Key, Compare> {
|
||||||
|
public:
|
||||||
|
INLINE ov_multiset(const Compare &compare = Compare());
|
||||||
|
INLINE ov_multiset(const ov_multiset<Key, Compare> ©);
|
||||||
|
INLINE ov_multiset<Key, Compare> &operator = (const ov_multiset<Key, Compare> ©);
|
||||||
|
|
||||||
|
INLINE iterator insert(iterator position, const value_type &key);
|
||||||
|
INLINE pair<iterator, bool> insert(const value_type &key);
|
||||||
|
|
||||||
|
INLINE void sort();
|
||||||
|
};
|
||||||
|
|
||||||
#include "ordered_vector.I"
|
#include "ordered_vector.I"
|
||||||
#include "ordered_vector.T"
|
#include "ordered_vector.T"
|
||||||
|
|
||||||
|
@ -18,7 +18,7 @@
|
|||||||
|
|
||||||
#include "ordered_vector.h"
|
#include "ordered_vector.h"
|
||||||
|
|
||||||
typedef ordered_vector<int> myvec;
|
typedef ov_multiset<int> myvec;
|
||||||
|
|
||||||
void
|
void
|
||||||
search(myvec &v, int element) {
|
search(myvec &v, int element) {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user