1ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru/* 2ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru********************************************************************** 385bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho* Copyright (C) 1999-2009, International Business Machines 4ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru* Corporation and others. All Rights Reserved. 5ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru********************************************************************** 6ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru* Date Name Description 7ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru* 10/22/99 alan Creation. This is an internal header. 8ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru* It should not be exported. 9ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru********************************************************************** 10ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru*/ 11ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 12ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#ifndef UVECTOR_H 13ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#define UVECTOR_H 14ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 15ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#include "unicode/utypes.h" 16ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#include "unicode/uobject.h" 17ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#include "uhash.h" 18ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 19ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste QueruU_NAMESPACE_BEGIN 20ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 21ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru/** 22ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * A token comparison function. 23ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * @param tok1 A token (object or integer) 24ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * @param tok2 A token (object or integer) 25ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * @return 0 if the two tokens are equal, -1 if tok1 is < tok2, or 26ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * +1 if tok1 is > tok2. 27ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 28ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querutypedef int8_t U_CALLCONV USortComparator(UHashTok tok1, 29ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UHashTok tok2); 30ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 31ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru/** 32ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * A token assignment function. It may copy an integer, copy 33ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * a pointer, or clone a pointer, as appropriate. 34ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * @param dst The token to be assigned to 35ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * @param src The token to assign from 36ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 37ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querutypedef void U_CALLCONV UTokenAssigner(UHashTok *dst, 38ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UHashTok *src); 39ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 40ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru/** 41ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p>Ultralightweight C++ implementation of a <tt>void*</tt> vector 42ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * that is (mostly) compatible with java.util.Vector. 43ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 44ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p>This is a very simple implementation, written to satisfy an 45ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * immediate porting need. As such, it is not completely fleshed out, 46ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * and it aims for simplicity and conformity. Nonetheless, it serves 47ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * its purpose (porting code from java that uses java.util.Vector) 48ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * well, and it could be easily made into a more robust vector class. 49ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 50ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p><b>Design notes</b> 51ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 52ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p>There is index bounds checking, but little is done about it. If 53ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * indices are out of bounds, either nothing happens, or zero is 54ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * returned. We <em>do</em> avoid indexing off into the weeds. 55ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 56ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p>There is detection of out of memory, but the handling is very 57ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * coarse-grained -- similar to UnicodeString's protocol, but even 58ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * coarser. The class contains <em>one static flag</em> that is set 59ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * when any call to <tt>new</tt> returns zero. This allows the caller 60ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * to use several vectors and make just one check at the end to see if 61ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * a memory failure occurred. This is more efficient than making a 62ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * check after each call on each vector when doing many operations on 63ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * multiple vectors. The single static flag works best when memory 64ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * failures are infrequent, and when recovery options are limited or 65ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * nonexistent. 66ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 67ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p>Since we don't have garbage collection, UVector was given the 68ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * option to <em>own</em>its contents. To employ this, set a deleter 69ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * function. The deleter is called on a void* pointer when that 70ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * pointer is released by the vector, either when the vector itself is 71ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * destructed, or when a call to setElementAt() overwrites an element, 72ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * or when a call to remove() or one of its variants explicitly 73ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * removes an element. If no deleter is set, or the deleter is set to 74ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * zero, then it is assumed that the caller will delete elements as 75ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * needed. 76ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 77ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p>In order to implement methods such as contains() and indexOf(), 78ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * UVector needs a way to compare objects for equality. To do so, it 79ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * uses a comparison frunction, or "comparer." If the comparer is not 80ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * set, or is set to zero, then all such methods will act as if the 81ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * vector contains no element. That is, indexOf() will always return 82ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * -1, contains() will always return FALSE, etc. 83ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 84ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p><b>To do</b> 85ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 86ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p>Improve the handling of index out of bounds errors. 87ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 88ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * @author Alan Liu 89ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 90ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruclass U_COMMON_API UVector : public UObject { 91ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // NOTE: UVector uses the UHashKey (union of void* and int32_t) as 92ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // its basic storage type. It uses UKeyComparator as its 93ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // comparison function. It uses UObjectDeleter as its deleter 94ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // function. These are named for hashtables, but used here as-is 95ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // rather than duplicating the type. This allows sharing of 96ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // support functions. 97ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 98ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruprivate: 99ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t count; 100ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 101ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t capacity; 102ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 103ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UHashTok* elements; 104ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 105ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UObjectDeleter *deleter; 106ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 107ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UKeyComparator *comparer; 108ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 109ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querupublic: 110ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UVector(UErrorCode &status); 111ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 112ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UVector(int32_t initialCapacity, UErrorCode &status); 113ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 114ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UVector(UObjectDeleter *d, UKeyComparator *c, UErrorCode &status); 115ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 116ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UVector(UObjectDeleter *d, UKeyComparator *c, int32_t initialCapacity, UErrorCode &status); 117ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 118ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru virtual ~UVector(); 119ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 120ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 121ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Assign this object to another (make this a copy of 'other'). 122ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Use the 'assign' function to assign each element. 123ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 124ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void assign(const UVector& other, UTokenAssigner *assign, UErrorCode &ec); 125ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 126ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 127ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Compare this vector with another. They will be considered 128ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * equal if they are of the same size and all elements are equal, 129ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * as compared using this object's comparer. 130ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 131ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool operator==(const UVector& other); 132ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 133ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 134ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Equivalent to !operator==() 135ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 136ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru inline UBool operator!=(const UVector& other); 137ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 138ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru //------------------------------------------------------------ 139ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // java.util.Vector API 140ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru //------------------------------------------------------------ 141ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 142ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void addElement(void* obj, UErrorCode &status); 143ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 144ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void addElement(int32_t elem, UErrorCode &status); 145ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 146ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void setElementAt(void* obj, int32_t index); 147ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 148ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void setElementAt(int32_t elem, int32_t index); 149ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 150ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void insertElementAt(void* obj, int32_t index, UErrorCode &status); 151ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 152ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void insertElementAt(int32_t elem, int32_t index, UErrorCode &status); 153ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 154ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void* elementAt(int32_t index) const; 155ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 156ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t elementAti(int32_t index) const; 157ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 158ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool equals(const UVector &other) const; 159ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 160ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void* firstElement(void) const; 161ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 162ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void* lastElement(void) const; 163ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 164ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t lastElementi(void) const; 165ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 166ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t indexOf(void* obj, int32_t startIndex = 0) const; 167ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 168ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t indexOf(int32_t obj, int32_t startIndex = 0) const; 169ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 170ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool contains(void* obj) const; 171ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 172ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool contains(int32_t obj) const; 173ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 174ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool containsAll(const UVector& other) const; 175ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 176ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool removeAll(const UVector& other); 177ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 178ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool retainAll(const UVector& other); 179ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 180ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void removeElementAt(int32_t index); 181ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 182ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool removeElement(void* obj); 183ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 184ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void removeAllElements(); 185ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 186ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t size(void) const; 187ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 188ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool isEmpty(void) const; 189ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 190ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool ensureCapacity(int32_t minimumCapacity, UErrorCode &status); 191ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 192ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 193ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Change the size of this vector as follows: If newSize is 194ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * smaller, then truncate the array, possibly deleting held 195ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * elements for i >= newSize. If newSize is larger, grow the 196ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * array, filling in new slots with NULL. 197ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 19885bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho void setSize(int32_t newSize, UErrorCode &status); 199ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 200ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 201ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Fill in the given array with all elements of this vector. 202ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 203ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void** toArray(void** result) const; 204ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 205ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru //------------------------------------------------------------ 206ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // New API 207ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru //------------------------------------------------------------ 208ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 209ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UObjectDeleter *setDeleter(UObjectDeleter *d); 210ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 211ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UKeyComparator *setComparer(UKeyComparator *c); 212ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 213ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void* operator[](int32_t index) const; 214ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 215ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 216ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Removes the element at the given index from this vector and 217ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * transfer ownership of it to the caller. After this call, the 218ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * caller owns the result and must delete it and the vector entry 219ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * at 'index' is removed, shifting all subsequent entries back by 220ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * one index and shortening the size of the vector by one. If the 221ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * index is out of range or if there is no item at the given index 222ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * then 0 is returned and the vector is unchanged. 223ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 224ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void* orphanElementAt(int32_t index); 225ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 226ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 227ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Returns true if this vector contains none of the elements 228ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * of the given vector. 229ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * @param other vector to be checked for containment 230ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * @return true if the test condition is met 231ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 232ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool containsNone(const UVector& other) const; 233ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 234ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 235ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Insert the given object into this vector at its sorted position 236ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * as defined by 'compare'. The current elements are assumed to 237ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * be sorted already. 238ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 239ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void sortedInsert(void* obj, USortComparator *compare, UErrorCode& ec); 240ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 241ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 242ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Insert the given integer into this vector at its sorted position 243ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * as defined by 'compare'. The current elements are assumed to 244ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * be sorted already. 245ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 246ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void sortedInsert(int32_t obj, USortComparator *compare, UErrorCode& ec); 247ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 248ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 24985bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho * Sort the contents of the vector, assuming that the contents of the 25085bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho * vector are of type int32_t. 25185bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho */ 25285bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho void sorti(UErrorCode &ec); 25385bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho 25485bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho /** 25585bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho * Sort the contents of this vector, using a caller-supplied function 25685bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho * to do the comparisons. (It's confusing that 25785bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho * UVector's USortComparator function is different from the 25885bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho * UComparator function type defined in uarrsort.h) 25985bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho */ 26085bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho void sort(USortComparator *compare, UErrorCode &ec); 26185bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho 26285bf2e2fbc60a9f938064abc8127d61da7d19882Claire Ho /** 263ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * ICU "poor man's RTTI", returns a UClassID for this class. 264ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 265ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru static UClassID U_EXPORT2 getStaticClassID(); 266ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 267ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 268ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * ICU "poor man's RTTI", returns a UClassID for the actual class. 269ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 270ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru virtual UClassID getDynamicClassID() const; 271ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 272ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruprivate: 273ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void _init(int32_t initialCapacity, UErrorCode &status); 274ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 275ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t indexOf(UHashTok key, int32_t startIndex = 0, int8_t hint = 0) const; 276ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 277ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void sortedInsert(UHashTok tok, USortComparator *compare, UErrorCode& ec); 278ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 279ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // Disallow 280ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UVector(const UVector&); 281ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 282ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // Disallow 283ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UVector& operator=(const UVector&); 284ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 285ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}; 286ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 287ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 288ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru/** 289ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p>Ultralightweight C++ implementation of a <tt>void*</tt> stack 290ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * that is (mostly) compatible with java.util.Stack. As in java, this 291ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * is merely a paper thin layer around UVector. See the UVector 292ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * documentation for further information. 293ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 294ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p><b>Design notes</b> 295ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 296ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p>The element at index <tt>n-1</tt> is (of course) the top of the 297ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * stack. 298ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 299ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * <p>The poorly named <tt>empty()</tt> method doesn't empty the 300ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * stack; it determines if the stack is empty. 301ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * 302ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * @author Alan Liu 303ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 304ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruclass U_COMMON_API UStack : public UVector { 305ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querupublic: 306ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UStack(UErrorCode &status); 307ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 308ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UStack(int32_t initialCapacity, UErrorCode &status); 309ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 310ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UStack(UObjectDeleter *d, UKeyComparator *c, UErrorCode &status); 311ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 312ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UStack(UObjectDeleter *d, UKeyComparator *c, int32_t initialCapacity, UErrorCode &status); 313ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 314ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru virtual ~UStack(); 315ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 316ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // It's okay not to have a virtual destructor (in UVector) 317ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // because UStack has no special cleanup to do. 318ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 319ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UBool empty(void) const; 320ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 321ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void* peek(void) const; 322ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 323ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t peeki(void) const; 324ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 325ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void* pop(void); 326ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 327ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t popi(void); 328ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 329ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru void* push(void* obj, UErrorCode &status); 330ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 331ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t push(int32_t i, UErrorCode &status); 332ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 333ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /* 334ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru If the object o occurs as an item in this stack, 335ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru this method returns the 1-based distance from the top of the stack. 336ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 337ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru int32_t search(void* obj) const; 338ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 339ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 340ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * ICU "poor man's RTTI", returns a UClassID for this class. 341ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 342ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru static UClassID U_EXPORT2 getStaticClassID(); 343ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 344ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru /** 345ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * ICU "poor man's RTTI", returns a UClassID for the actual class. 346ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */ 347ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru virtual UClassID getDynamicClassID() const; 348ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 349ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruprivate: 350ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // Disallow 351ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UStack(const UStack&); 352ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 353ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru // Disallow 354ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru UStack& operator=(const UStack&); 355ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}; 356ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 357ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 358ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru// UVector inlines 359ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 360ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline int32_t UVector::size(void) const { 361ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return count; 362ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 363ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 364ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline UBool UVector::isEmpty(void) const { 365ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return count == 0; 366ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 367ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 368ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline UBool UVector::contains(void* obj) const { 369ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return indexOf(obj) >= 0; 370ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 371ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 372ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline UBool UVector::contains(int32_t obj) const { 373ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return indexOf(obj) >= 0; 374ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 375ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 376ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline void* UVector::firstElement(void) const { 377ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return elementAt(0); 378ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 379ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 380ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline void* UVector::lastElement(void) const { 381ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return elementAt(count-1); 382ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 383ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 384ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline int32_t UVector::lastElementi(void) const { 385ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return elementAti(count-1); 386ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 387ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 388ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline void* UVector::operator[](int32_t index) const { 389ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return elementAt(index); 390ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 391ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 392ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline UBool UVector::operator!=(const UVector& other) { 393ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return !operator==(other); 394ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 395ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 396ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru// UStack inlines 397ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 398ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline UBool UStack::empty(void) const { 399ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return isEmpty(); 400ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 401ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 402ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline void* UStack::peek(void) const { 403ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return lastElement(); 404ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 405ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 406ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline int32_t UStack::peeki(void) const { 407ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return lastElementi(); 408ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 409ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 410ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline void* UStack::push(void* obj, UErrorCode &status) { 411ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru addElement(obj, status); 412ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return obj; 413ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 414ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 415ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruinline int32_t UStack::push(int32_t i, UErrorCode &status) { 416ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru addElement(i, status); 417ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru return i; 418ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru} 419ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 420ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste QueruU_NAMESPACE_END 421ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru 422ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#endif 423