uvectr32.h revision 51cfa1a9a96cad34675a6415fe86dfdf3f525bb6
1/* 2********************************************************************** 3* Copyright (C) 1999-2006, International Business Machines 4* Corporation and others. All Rights Reserved. 5********************************************************************** 6*/ 7 8// 9// UVector32 is a class implementing a vector of 32 bit integers. 10// It is similar to UVector, but holds int32_t values rather than pointers. 11// Most of the code is unchanged from UVector. 12// 13 14#ifndef UVECTOR32_H 15#define UVECTOR32_H 16 17#include "unicode/utypes.h" 18#include "unicode/uobject.h" 19#include "uhash.h" 20#include "uassert.h" 21 22U_NAMESPACE_BEGIN 23 24 25 26/** 27 * <p>Ultralightweight C++ implementation of a <tt>void*</tt> vector 28 * that is (mostly) compatible with java.util.Vector. 29 * 30 * <p>This is a very simple implementation, written to satisfy an 31 * immediate porting need. As such, it is not completely fleshed out, 32 * and it aims for simplicity and conformity. Nonetheless, it serves 33 * its purpose (porting code from java that uses java.util.Vector) 34 * well, and it could be easily made into a more robust vector class. 35 * 36 * <p><b>Design notes</b> 37 * 38 * <p>There is index bounds checking, but little is done about it. If 39 * indices are out of bounds, either nothing happens, or zero is 40 * returned. We <em>do</em> avoid indexing off into the weeds. 41 * 42 * <p>There is detection of out of memory, but the handling is very 43 * coarse-grained -- similar to UnicodeString's protocol, but even 44 * coarser. The class contains <em>one static flag</em> that is set 45 * when any call to <tt>new</tt> returns zero. This allows the caller 46 * to use several vectors and make just one check at the end to see if 47 * a memory failure occurred. This is more efficient than making a 48 * check after each call on each vector when doing many operations on 49 * multiple vectors. The single static flag works best when memory 50 * failures are infrequent, and when recovery options are limited or 51 * nonexistent. 52 * 53 * <p><b>To do</b> 54 * 55 * <p>Improve the handling of index out of bounds errors. 56 * 57 * @author Alan Liu 58 */ 59class U_COMMON_API UVector32 : public UObject { 60private: 61 int32_t count; 62 63 int32_t capacity; 64 65 int32_t* elements; 66 67public: 68 UVector32(UErrorCode &status); 69 70 UVector32(int32_t initialCapacity, UErrorCode &status); 71 72 virtual ~UVector32(); 73 74 /** 75 * Assign this object to another (make this a copy of 'other'). 76 * Use the 'assign' function to assign each element. 77 */ 78 void assign(const UVector32& other, UErrorCode &ec); 79 80 /** 81 * Compare this vector with another. They will be considered 82 * equal if they are of the same size and all elements are equal, 83 * as compared using this object's comparer. 84 */ 85 UBool operator==(const UVector32& other); 86 87 /** 88 * Equivalent to !operator==() 89 */ 90 inline UBool operator!=(const UVector32& other); 91 92 //------------------------------------------------------------ 93 // java.util.Vector API 94 //------------------------------------------------------------ 95 96 void addElement(int32_t elem, UErrorCode &status); 97 98 void setElementAt(int32_t elem, int32_t index); 99 100 void insertElementAt(int32_t elem, int32_t index, UErrorCode &status); 101 102 int32_t elementAti(int32_t index) const; 103 104 UBool equals(const UVector32 &other) const; 105 106 int32_t lastElementi(void) const; 107 108 int32_t indexOf(int32_t elem, int32_t startIndex = 0) const; 109 110 UBool contains(int32_t elem) const; 111 112 UBool containsAll(const UVector32& other) const; 113 114 UBool removeAll(const UVector32& other); 115 116 UBool retainAll(const UVector32& other); 117 118 void removeElementAt(int32_t index); 119 120 void removeAllElements(); 121 122 int32_t size(void) const; 123 124 UBool isEmpty(void) const; 125 126 // Inline. Use this one for speedy size check. 127 inline UBool ensureCapacity(int32_t minimumCapacity, UErrorCode &status); 128 129 // Out-of-line, handles actual growth. Called by ensureCapacity() when necessary. 130 UBool expandCapacity(int32_t minimumCapacity, UErrorCode &status); 131 132 /** 133 * Change the size of this vector as follows: If newSize is 134 * smaller, then truncate the array, possibly deleting held 135 * elements for i >= newSize. If newSize is larger, grow the 136 * array, filling in new slows with zero. 137 */ 138 void setSize(int32_t newSize); 139 140 //------------------------------------------------------------ 141 // New API 142 //------------------------------------------------------------ 143 144 /** 145 * Returns true if this vector contains none of the elements 146 * of the given vector. 147 * @param other vector to be checked for containment 148 * @return true if the test condition is met 149 */ 150 UBool containsNone(const UVector32& other) const; 151 152 153 /** 154 * Insert the given integer into this vector at its sorted position. 155 * The current elements are assumed to be sorted already. 156 */ 157 void sortedInsert(int32_t elem, UErrorCode& ec); 158 159 /** 160 * Returns a pointer to the internal array holding the vector. 161 */ 162 int32_t *getBuffer() const; 163 164 /** 165 * ICU "poor man's RTTI", returns a UClassID for this class. 166 */ 167 static UClassID U_EXPORT2 getStaticClassID(); 168 169 /** 170 * ICU "poor man's RTTI", returns a UClassID for the actual class. 171 */ 172 virtual UClassID getDynamicClassID() const; 173 174private: 175 void _init(int32_t initialCapacity, UErrorCode &status); 176 177 // Disallow 178 UVector32(const UVector32&); 179 180 // Disallow 181 UVector32& operator=(const UVector32&); 182 183 184 // API Functions for Stack operations. 185 // In the original UVector, these were in a separate derived class, UStack. 186 // Here in UVector32, they are all together. 187public: 188 UBool empty(void) const; // TODO: redundant, same as empty(). Remove it? 189 190 int32_t peeki(void) const; 191 192 int32_t popi(void); 193 194 int32_t push(int32_t i, UErrorCode &status); 195 196 int32_t *reserveBlock(int32_t size, UErrorCode &status); 197 int32_t *popFrame(int32_t size); 198}; 199 200 201// UVector32 inlines 202 203inline UBool UVector32::ensureCapacity(int32_t minimumCapacity, UErrorCode &status) { 204 if (capacity >= minimumCapacity) { 205 return TRUE; 206 } else { 207 return expandCapacity(minimumCapacity, status); 208 } 209} 210 211inline int32_t UVector32::elementAti(int32_t index) const { 212 return (0 <= index && index < count) ? elements[index] : 0; 213} 214 215 216inline void UVector32::addElement(int32_t elem, UErrorCode &status) { 217 if (ensureCapacity(count + 1, status)) { 218 elements[count] = elem; 219 count++; 220 } 221} 222 223inline int32_t *UVector32::reserveBlock(int32_t size, UErrorCode &status) { 224 ensureCapacity(count+size, status); 225 int32_t *rp = elements+count; 226 count += size; 227 return rp; 228} 229 230inline int32_t *UVector32::popFrame(int32_t size) { 231 U_ASSERT(count >= size); 232 count -= size; 233 if (count < 0) { 234 count = 0; 235 } 236 return elements+count-size; 237} 238 239 240 241inline int32_t UVector32::size(void) const { 242 return count; 243} 244 245inline UBool UVector32::isEmpty(void) const { 246 return count == 0; 247} 248 249inline UBool UVector32::contains(int32_t obj) const { 250 return indexOf(obj) >= 0; 251} 252 253inline int32_t UVector32::lastElementi(void) const { 254 return elementAti(count-1); 255} 256 257inline UBool UVector32::operator!=(const UVector32& other) { 258 return !operator==(other); 259} 260 261inline int32_t *UVector32::getBuffer() const { 262 return elements; 263} 264 265 266// UStack inlines 267 268inline UBool UVector32::empty(void) const { 269 return isEmpty(); 270} 271 272inline int32_t UVector32::peeki(void) const { 273 return lastElementi(); 274} 275 276inline int32_t UVector32::push(int32_t i, UErrorCode &status) { 277 addElement(i, status); 278 return i; 279} 280 281inline int32_t UVector32::popi(void) { 282 int32_t result = 0; 283 if (count > 0) { 284 count--; 285 result = elements[count]; 286 } 287 return result; 288} 289 290U_NAMESPACE_END 291 292#endif 293