diff --git a/icu4c/source/common/uvector.cpp b/icu4c/source/common/uvector.cpp index e01244f0fcb..81430ee2400 100644 --- a/icu4c/source/common/uvector.cpp +++ b/icu4c/source/common/uvector.cpp @@ -74,6 +74,37 @@ UVector::~UVector() { elements = 0; } +/** + * Assign this object to another (make this a copy of 'other'). + * Use the 'assign' function to assign each element. + */ +void UVector::assign(const UVector& other, UTokenAssigner assign, UErrorCode &ec) { + if (ensureCapacity(other.count, ec)) { + setSize(other.count); + for (int32_t i=0; i= 0) { + return FALSE; + } + } + return TRUE; +} + +UBool UVector::removeAll(const UVector& other) { + UBool changed = FALSE; + for (int32_t i=0; i= 0) { + removeElementAt(j); + changed = TRUE; + } + } + return changed; +} + +UBool UVector::retainAll(const UVector& other) { + UBool changed = FALSE; + for (int32_t j=size()-1; j>=0; --j) { + int32_t i = other.indexOf(elements[j]); + if (i < 0) { + removeElementAt(j); + changed = TRUE; + } + } + return changed; +} + void UVector::removeElementAt(int32_t index) { void* e = orphanElementAt(index); if (e != 0 && deleter != 0) { @@ -154,23 +227,22 @@ void UVector::removeAllElements(void) { } int32_t UVector::indexOf(void* obj, int32_t startIndex) const { - if (comparer != 0) { - UHashTok key; - key.pointer = obj; - for (int32_t i=startIndex; i 0) { + max = probe; + } else { + // assert(c <= 0); + min = probe + 1; + } + } + if (ensureCapacity(count + 1, ec)) { + for (int32_t i=count; i>min; --i) { + elements[i] = elements[i-1]; + } + elements[min] = tok; + ++count; + } +} + UStack::UStack(UErrorCode &status) : UVector(status) { diff --git a/icu4c/source/common/uvector.h b/icu4c/source/common/uvector.h index c95d0bde324..c79053ee53d 100644 --- a/icu4c/source/common/uvector.h +++ b/icu4c/source/common/uvector.h @@ -17,6 +17,25 @@ U_NAMESPACE_BEGIN +/** + * A token comparison function. + * @param tok1 A token (object or integer) + * @param tok2 A token (object or integer) + * @return 0 if the two tokens are equal, -1 if tok1 is < tok2, or + * +1 if tok1 is > tok2. + */ +typedef int8_t (U_EXPORT2 * U_CALLCONV USortComparator)(UHashTok tok1, + UHashTok tok2); + +/** + * A token assignment function. It may copy an integer, copy + * a pointer, or clone a pointer, as appropriate. + * @param dst The token to be assigned to + * @param src The token to assign from + */ +typedef void (U_EXPORT2 * U_CALLCONV UTokenAssigner)(UHashTok dst, + UHashTok src); + /** *

Ultralightweight C++ implementation of a void* vector * that is (mostly) compatible with java.util.Vector. @@ -94,8 +113,27 @@ public: UVector(UObjectDeleter d, UKeyComparator c, UErrorCode &status); UVector(UObjectDeleter d, UKeyComparator c, int32_t initialCapacity, UErrorCode &status); + ~UVector(); + /** + * Assign this object to another (make this a copy of 'other'). + * Use the 'assign' function to assign each element. + */ + void assign(const UVector& other, UTokenAssigner assign, UErrorCode &ec); + + /** + * Compare this vector with another. They will be considered + * equal if they are of the same size and all elements are equal, + * as compared using this object's comparer. + */ + UBool operator==(const UVector& other); + + /** + * Equivalent to !operator==() + */ + inline UBool operator!=(const UVector& other); + //------------------------------------------------------------ // java.util.Vector API //------------------------------------------------------------ @@ -128,6 +166,12 @@ public: UBool contains(int32_t obj) const; + UBool containsAll(const UVector& other) const; + + UBool removeAll(const UVector& other); + + UBool retainAll(const UVector& other); + void removeElementAt(int32_t index); UBool removeElement(void* obj); @@ -174,9 +218,35 @@ public: */ void* orphanElementAt(int32_t index); + /** + * Returns true if this vector contains none of the elements + * of the given vector. + * @param other vector to be checked for containment + * @return true if the test condition is met + */ + UBool containsNone(const UVector& other) const; + + /** + * Insert the given object into this vector at its sorted position + * as defined by 'compare'. The current elements are assumed to + * be sorted already. + */ + void sortedInsert(void* obj, USortComparator compare, UErrorCode& ec); + + /** + * Insert the given integer into this vector at its sorted position + * as defined by 'compare'. The current elements are assumed to + * be sorted already. + */ + void sortedInsert(int32_t obj, USortComparator compare, UErrorCode& ec); + private: void _init(int32_t initialCapacity, UErrorCode &status); + int32_t indexOf(UHashTok key, int32_t startIndex = 0) const; + + void sortedInsert(UHashTok tok, USortComparator compare, UErrorCode& ec); + // Disallow UVector(const UVector&); @@ -273,6 +343,10 @@ inline void* UVector::operator[](int32_t index) const { return elementAt(index); } +inline UBool UVector::operator!=(const UVector& other) { + return !operator==(other); +} + // UStack inlines inline UBool UStack::empty(void) const {