From b70227e2c7810a1059bf95db740f1e0931f0aefd Mon Sep 17 00:00:00 2001 From: Ram Viswanadha Date: Fri, 11 Nov 2005 19:23:09 +0000 Subject: [PATCH] ICU-4741 make compare functions for Hashtable and StringEnumeration general X-SVN-Rev: 18788 --- icu4c/source/common/hash.h | 42 +++++- icu4c/source/common/locid.cpp | 2 +- icu4c/source/common/rbbiscan.cpp | 2 +- icu4c/source/common/rbbistbl.cpp | 2 +- icu4c/source/common/ucnv_bld.c | 2 +- icu4c/source/common/udata.c | 2 +- icu4c/source/common/uhash.c | 79 +++++++++-- icu4c/source/common/uhash.h | 34 ++++- icu4c/source/common/unicode/strenum.h | 17 +++ icu4c/source/common/uresbund.c | 2 +- icu4c/source/common/usprep.cpp | 2 +- icu4c/source/common/ustrenum.cpp | 7 +- icu4c/source/i18n/anytrans.cpp | 4 +- icu4c/source/i18n/astro.cpp | 2 +- icu4c/source/i18n/dtfmtsym.cpp | 167 ++++++++++-------------- icu4c/source/i18n/olsontz.cpp | 8 +- icu4c/source/i18n/smpdtfmt.cpp | 49 ------- icu4c/source/i18n/ucol_elm.cpp | 2 +- icu4c/source/i18n/ucol_tok.cpp | 2 +- icu4c/source/i18n/unicode/dtfmtsym.h | 12 +- icu4c/source/i18n/unicode/smpdtfmt.h | 6 - icu4c/source/test/cintltst/chashtst.c | 8 +- icu4c/source/test/intltest/dtfmttst.cpp | 5 + icu4c/source/test/intltest/tsdtfmsy.cpp | 7 +- icu4c/source/tools/gensprep/store.c | 2 +- 25 files changed, 257 insertions(+), 210 deletions(-) diff --git a/icu4c/source/common/hash.h b/icu4c/source/common/hash.h index f1ea543cb67..9a148668999 100644 --- a/icu4c/source/common/hash.h +++ b/icu4c/source/common/hash.h @@ -1,6 +1,6 @@ /* ****************************************************************************** -* Copyright (C) 1997-2004, International Business Machines +* Copyright (C) 1997-2005, International Business Machines * Corporation and others. All Rights Reserved. ****************************************************************************** * Date Name Description @@ -27,7 +27,7 @@ U_NAMESPACE_BEGIN class U_COMMON_API Hashtable : public UMemory { UHashtable* hash; - inline void init(UHashFunction *keyHash, UKeyComparator *keyComp, UErrorCode& status); + inline void init(UHashFunction *keyHash, UKeyComparator *keyComp, UValueComparator *valueComp, UErrorCode& status); public: /** @@ -37,6 +37,14 @@ public: */ Hashtable(UBool ignoreKeyCase, UErrorCode& status); + /** + * Construct a hashtable + * @param keyComp Compartor for comparing the keys + * @param valueComp Compartor for comparing the values + * @param status Error code + */ + Hashtable(UKeyComparator *keyComp, UValueComparator *valueComp, UErrorCode& status); + /** * Construct a hashtable * @param status Error code @@ -76,7 +84,12 @@ public: const UHashElement* find(const UnicodeString& key) const; const UHashElement* nextElement(int32_t& pos) const; + + UKeyComparator* setKeyCompartor(UKeyComparator*keyComp); + + UValueComparator* setValueCompartor(UValueComparator* valueComp); + UBool equals(const Hashtable& that) const; private: Hashtable(const Hashtable &other); // forbid copying of this class Hashtable &operator=(const Hashtable &other); // forbid copying of this class @@ -86,16 +99,21 @@ private: * Implementation ********************************************************************/ -inline void Hashtable::init(UHashFunction *keyHash, UKeyComparator *keyComp, UErrorCode& status) { +inline void Hashtable::init(UHashFunction *keyHash, UKeyComparator *keyComp, + UValueComparator *valueComp, UErrorCode& status) { if (U_FAILURE(status)) { return; } - hash = uhash_open(keyHash, keyComp, &status); + hash = uhash_open(keyHash, keyComp, valueComp, &status); if (U_SUCCESS(status)) { uhash_setKeyDeleter(hash, uhash_deleteUnicodeString); } } +inline Hashtable::Hashtable(UKeyComparator *keyComp, UValueComparator *valueComp, + UErrorCode& status): hash(0){ + init( uhash_hashUnicodeString, keyComp, valueComp, status); +} inline Hashtable::Hashtable(UBool ignoreKeyCase, UErrorCode& status) : hash(0) { @@ -103,20 +121,21 @@ inline Hashtable::Hashtable(UBool ignoreKeyCase, UErrorCode& status) : uhash_hashUnicodeString, ignoreKeyCase ? uhash_compareCaselessUnicodeString : uhash_compareUnicodeString, + NULL, status); } inline Hashtable::Hashtable(UErrorCode& status) : hash(0) { - init(uhash_hashUnicodeString, uhash_compareUnicodeString, status); + init(uhash_hashUnicodeString, uhash_compareUnicodeString, NULL, status); } inline Hashtable::Hashtable() : hash(0) { UErrorCode status = U_ZERO_ERROR; - init(uhash_hashUnicodeString, uhash_compareUnicodeString, status); + init(uhash_hashUnicodeString, uhash_compareUnicodeString, NULL, status); } inline Hashtable::~Hashtable() { @@ -170,6 +189,17 @@ inline void Hashtable::removeAll(void) { uhash_removeAll(hash); } +inline UKeyComparator* Hashtable::setKeyCompartor(UKeyComparator*keyComp){ + return uhash_setKeyComparator(hash, keyComp); +} + +inline UValueComparator* Hashtable::setValueCompartor(UValueComparator* valueComp){ + return uhash_setValueComparator(hash, valueComp); +} + +inline UBool Hashtable::equals(const Hashtable& that)const{ + return uhash_equals(hash, that.hash); +} U_NAMESPACE_END #endif diff --git a/icu4c/source/common/locid.cpp b/icu4c/source/common/locid.cpp index df5e40a6bb7..042976e0cc6 100644 --- a/icu4c/source/common/locid.cpp +++ b/icu4c/source/common/locid.cpp @@ -160,7 +160,7 @@ void locale_set_default_internal(const char *id) umtx_unlock(NULL); if (hashTableNeedsInit) { status = U_ZERO_ERROR; - UHashtable *tHashTable = uhash_open(uhash_hashChars, uhash_compareChars, &status); + UHashtable *tHashTable = uhash_open(uhash_hashChars, uhash_compareChars, NULL, &status); if (U_FAILURE(status)) { return; } diff --git a/icu4c/source/common/rbbiscan.cpp b/icu4c/source/common/rbbiscan.cpp index 8b3b6f21e00..02f1813bea1 100644 --- a/icu4c/source/common/rbbiscan.cpp +++ b/icu4c/source/common/rbbiscan.cpp @@ -142,7 +142,7 @@ RBBIRuleScanner::RBBIRuleScanner(RBBIRuleBuilder *rb) } fSymbolTable = new RBBISymbolTable(this, rb->fRules, *rb->fStatus); - fSetTable = uhash_open(uhash_hashUnicodeString, uhash_compareUnicodeString, rb->fStatus); + fSetTable = uhash_open(uhash_hashUnicodeString, uhash_compareUnicodeString, NULL, rb->fStatus); uhash_setValueDeleter(fSetTable, RBBISetTable_deleter); } diff --git a/icu4c/source/common/rbbistbl.cpp b/icu4c/source/common/rbbistbl.cpp index 56676538ac0..771eb3136a4 100644 --- a/icu4c/source/common/rbbistbl.cpp +++ b/icu4c/source/common/rbbistbl.cpp @@ -44,7 +44,7 @@ RBBISymbolTable::RBBISymbolTable(RBBIRuleScanner *rs, const UnicodeString &rules fHashTable = NULL; fCachedSetLookup = NULL; - fHashTable = uhash_open(uhash_hashUnicodeString, uhash_compareUnicodeString, &status); + fHashTable = uhash_open(uhash_hashUnicodeString, uhash_compareUnicodeString, NULL, &status); // uhash_open checks status if (U_FAILURE(status)) { return; diff --git a/icu4c/source/common/ucnv_bld.c b/icu4c/source/common/ucnv_bld.c index dbc8dd0269d..494c94aa20e 100644 --- a/icu4c/source/common/ucnv_bld.c +++ b/icu4c/source/common/ucnv_bld.c @@ -374,7 +374,7 @@ ucnv_shareConverterData(UConverterSharedData * data) if (SHARED_DATA_HASHTABLE == NULL) { - SHARED_DATA_HASHTABLE = uhash_openSize(uhash_hashChars, uhash_compareChars, + SHARED_DATA_HASHTABLE = uhash_openSize(uhash_hashChars, uhash_compareChars, NULL, ucnv_io_countTotalAliases(&err), &err); ucln_common_registerCleanup(UCLN_COMMON_UCNV, ucnv_cleanup); diff --git a/icu4c/source/common/udata.c b/icu4c/source/common/udata.c index dd8e5d5831f..097c377369f 100644 --- a/icu4c/source/common/udata.c +++ b/icu4c/source/common/udata.c @@ -218,7 +218,7 @@ static UHashtable *udata_getHashTable() { return gCommonDataCache; } - tHT = uhash_open(uhash_hashChars, uhash_compareChars, &err); + tHT = uhash_open(uhash_hashChars, uhash_compareChars, NULL, &err); uhash_setValueDeleter(tHT, DataCacheElement_deleter); umtx_lock(NULL); diff --git a/icu4c/source/common/uhash.c b/icu4c/source/common/uhash.c index f42593f0006..96a7d6dc01b 100644 --- a/icu4c/source/common/uhash.c +++ b/icu4c/source/common/uhash.c @@ -1,6 +1,6 @@ /* ****************************************************************************** -* Copyright (C) 1997-2004, International Business Machines +* Copyright (C) 1997-2005, International Business Machines * Corporation and others. All Rights Reserved. ****************************************************************************** * Date Name Description @@ -140,7 +140,9 @@ static const float RESIZE_POLICY_RATIO_TABLE[6] = { * PRIVATE Prototypes ********************************************************************/ -static UHashtable* _uhash_create(UHashFunction *keyHash, UKeyComparator *keyComp, +static UHashtable* _uhash_create(UHashFunction *keyHash, + UKeyComparator *keyComp, + UValueComparator *valueComp, int32_t primeIndex, UErrorCode *status); static void _uhash_allocate(UHashtable *hash, int32_t primeIndex, @@ -174,14 +176,18 @@ static void _uhash_internalSetResizePolicy(UHashtable *hash, enum UHashResizePol ********************************************************************/ U_CAPI UHashtable* U_EXPORT2 -uhash_open(UHashFunction *keyHash, UKeyComparator *keyComp, +uhash_open(UHashFunction *keyHash, + UKeyComparator *keyComp, + UValueComparator *valueComp, UErrorCode *status) { - return _uhash_create(keyHash, keyComp, 3, status); + return _uhash_create(keyHash, keyComp, valueComp, 3, status); } U_CAPI UHashtable* U_EXPORT2 -uhash_openSize(UHashFunction *keyHash, UKeyComparator *keyComp, +uhash_openSize(UHashFunction *keyHash, + UKeyComparator *keyComp, + UValueComparator *valueComp, int32_t size, UErrorCode *status) { @@ -191,7 +197,7 @@ uhash_openSize(UHashFunction *keyHash, UKeyComparator *keyComp, ++i; } - return _uhash_create(keyHash, keyComp, i, status); + return _uhash_create(keyHash, keyComp, valueComp, i, status); } U_CAPI void U_EXPORT2 @@ -224,6 +230,12 @@ uhash_setKeyComparator(UHashtable *hash, UKeyComparator *fn) { hash->keyComparator = fn; return result; } +U_CAPI UValueComparator *U_EXPORT2 +uhash_setValueComparator(UHashtable *hash, UValueComparator *fn){ + UValueComparator *result = hash->valueComparator; + hash->valueComparator = fn; + return result; +} U_CAPI UObjectDeleter *U_EXPORT2 uhash_setKeyDeleter(UHashtable *hash, UObjectDeleter *fn) { @@ -491,6 +503,48 @@ uhash_hashIChars(const UHashTok key) { STRING_HASH(uint8_t, key.pointer, uprv_strlen((char*)p), uprv_tolower(*p)); } +U_CAPI UBool U_EXPORT2 +uhash_equals(const UHashtable* hash1, const UHashtable* hash2){ + + int32_t count1, count2, pos, i; + + if(hash1==hash2){ + return TRUE; + } + + if(hash1==NULL || hash2==NULL){ + return FALSE; + } + /* make sure that we are comparing 2 hashes of the same type */ + if( hash1->keyComparator != hash2->keyComparator || + hash2->valueComparator != hash2->valueComparator){ + return FALSE; + } + + count1 = uhash_count(hash1); + count2 = uhash_count(hash2); + if(count1!=count2){ + return FALSE; + } + + pos=-1; + for(i=0; ikey; + const UHashTok val1 = elem1->value; + /* here the keys are not compared, instead the key form hash1 is used to fetch + * value from hash2. If the hashes are equal then then both hashes should + * contain equal values for the same key! + */ + const UHashElement* elem2 = _uhash_find(hash2, key1, hash2->keyHasher(key1)); + const UHashTok val2 = elem2->value; + if(hash1->valueComparator(val1, val2)==FALSE){ + return FALSE; + } + } + return TRUE; +} + /******************************************************************** * PUBLIC Comparator Functions ********************************************************************/ @@ -574,7 +628,9 @@ uhash_freeBlock(void *obj) { ********************************************************************/ static UHashtable* -_uhash_create(UHashFunction *keyHash, UKeyComparator *keyComp, +_uhash_create(UHashFunction *keyHash, + UKeyComparator *keyComp, + UValueComparator *valueComp, int32_t primeIndex, UErrorCode *status) { UHashtable *result; @@ -589,10 +645,11 @@ _uhash_create(UHashFunction *keyHash, UKeyComparator *keyComp, return NULL; } - result->keyHasher = keyHash; - result->keyComparator = keyComp; - result->keyDeleter = NULL; - result->valueDeleter = NULL; + result->keyHasher = keyHash; + result->keyComparator = keyComp; + result->valueComparator = valueComp; + result->keyDeleter = NULL; + result->valueDeleter = NULL; _uhash_internalSetResizePolicy(result, U_GROW); _uhash_allocate(result, primeIndex, status); diff --git a/icu4c/source/common/uhash.h b/icu4c/source/common/uhash.h index 9e26978813c..d579805bdec 100644 --- a/icu4c/source/common/uhash.h +++ b/icu4c/source/common/uhash.h @@ -1,6 +1,6 @@ /* ****************************************************************************** -* Copyright (C) 1997-2004, International Business Machines +* Copyright (C) 1997-2005, International Business Machines * Corporation and others. All Rights Reserved. ****************************************************************************** * Date Name Description @@ -117,7 +117,14 @@ typedef int32_t U_CALLCONV UHashFunction(const UHashTok key); */ typedef UBool U_CALLCONV UKeyComparator(const UHashTok key1, const UHashTok key2); - +/** + * A key comparison function. + * @param val1 A key stored in a hashtable + * @param val2 A key stored in a hashtable + * @return TRUE if the two keys are equal. + */ +typedef UBool U_CALLCONV UValueComparator(const UHashTok val1, + const UHashTok val2); /** * A function called by uhash_remove, * uhash_close, or uhash_put to delete @@ -169,6 +176,8 @@ struct UHashtable { * Never null. */ UKeyComparator *keyComparator; /* Compares keys for equality. * Never null. */ + UValueComparator *valueComparator; /* Compares the values for equality */ + UObjectDeleter *keyDeleter; /* Deletes keys when required. * If NULL won't do anything */ UObjectDeleter *valueDeleter; /* Deletes values when required. @@ -195,6 +204,7 @@ U_CDECL_END U_CAPI UHashtable* U_EXPORT2 uhash_open(UHashFunction *keyHash, UKeyComparator *keyComp, + UValueComparator *valueComp, UErrorCode *status); /** @@ -211,6 +221,7 @@ uhash_open(UHashFunction *keyHash, U_CAPI UHashtable* U_EXPORT2 uhash_openSize(UHashFunction *keyHash, UKeyComparator *keyComp, + UValueComparator *valueComp, int32_t size, UErrorCode *status); @@ -242,6 +253,16 @@ uhash_setKeyHasher(UHashtable *hash, UHashFunction *fn); U_CAPI UKeyComparator *U_EXPORT2 uhash_setKeyComparator(UHashtable *hash, UKeyComparator *fn); +/** + * Set the function used to compare values. The default comparison is a + * void* pointer comparison. + * @param hash The UHashtable to set + * @param fn the function to be used compare keys; must not be NULL + * @return the previous key comparator; non-NULL + */ +U_CAPI UValueComparator *U_EXPORT2 +uhash_setValueComparator(UHashtable *hash, UValueComparator *fn); + /** * Set the function used to delete keys. If this function pointer is * NULL, this hashtable does not delete keys. If it is non-NULL, this @@ -676,4 +697,13 @@ uhash_deleteUVector(void *obj); U_CAPI void U_EXPORT2 uhash_freeBlock(void *obj); +/** + * Checks if the given hash tables are equal or not. + * @param hash1 + * @param hash2 + * @return true if the hashtables are equal and false if not. + */ +U_CAPI UBool U_EXPORT2 +uhash_equals(const UHashtable* hash1, const UHashtable* hash2); + #endif diff --git a/icu4c/source/common/unicode/strenum.h b/icu4c/source/common/unicode/strenum.h index c75e4b223b6..0e085e26ff2 100644 --- a/icu4c/source/common/unicode/strenum.h +++ b/icu4c/source/common/unicode/strenum.h @@ -184,6 +184,23 @@ public: */ virtual void reset(UErrorCode& status) = 0; + /** + * Compares this enumeration to other to check if both are equal + * + * @param Other string enumeration to compare this object to + * @return TRUE if the enumerations are equal. FALSE if not. + * @draft ICU 3.6 + */ + virtual UBool operator==(const StringEnumeration& that)const; + /** + * Compares this enumeration to other to check if both are not equal + * + * @param Other string enumeration to compare this object to + * @return TRUE if the enumerations are equal. FALSE if not. + * @draft ICU 3.6 + */ + virtual UBool operator!=(const StringEnumeration& that)const {return !operator==(that);}; + protected: /** * UnicodeString field for use with default implementations and subclasses. diff --git a/icu4c/source/common/uresbund.c b/icu4c/source/common/uresbund.c index 5b94c8aa62a..084b13e924f 100644 --- a/icu4c/source/common/uresbund.c +++ b/icu4c/source/common/uresbund.c @@ -214,7 +214,7 @@ static void initCache(UErrorCode *status) { makeCache = (cache == NULL); umtx_unlock(&resbMutex); if(makeCache) { - UHashtable *newCache = uhash_open(hashEntry, compareEntries, status); + UHashtable *newCache = uhash_open(hashEntry, compareEntries, NULL, status); if (U_FAILURE(*status)) { return; } diff --git a/icu4c/source/common/usprep.cpp b/icu4c/source/common/usprep.cpp index 40eba2867dd..2839924051a 100644 --- a/icu4c/source/common/usprep.cpp +++ b/icu4c/source/common/usprep.cpp @@ -197,7 +197,7 @@ initCache(UErrorCode *status) { makeCache = (SHARED_DATA_HASHTABLE == NULL); umtx_unlock(&usprepMutex); if(makeCache) { - UHashtable *newCache = uhash_open(hashEntry, compareEntries, status); + UHashtable *newCache = uhash_open(hashEntry, compareEntries, NULL, status); if (U_FAILURE(*status)) { return; } diff --git a/icu4c/source/common/ustrenum.cpp b/icu4c/source/common/ustrenum.cpp index 22db32b87c1..5b5e1ae41ef 100644 --- a/icu4c/source/common/ustrenum.cpp +++ b/icu4c/source/common/ustrenum.cpp @@ -1,6 +1,6 @@ /* ********************************************************************** -* Copyright (c) 2002-2004, International Business Machines +* Copyright (c) 2002-2005, International Business Machines * Corporation and others. All Rights Reserved. ********************************************************************** * Author: Alan Liu @@ -111,6 +111,10 @@ StringEnumeration::setChars(const char *s, int32_t length, UErrorCode &status) { return NULL; } +UBool +StringEnumeration::operator==(const StringEnumeration& that)const{ + return getDynamicClassID() == that.getDynamicClassID(); +} // UStringEnumeration implementation --------------------------------------- *** @@ -311,3 +315,4 @@ uenum_openCharStringsEnumeration(const char** strings, int32_t count, return (UEnumeration*) result; } + diff --git a/icu4c/source/i18n/anytrans.cpp b/icu4c/source/i18n/anytrans.cpp index d46668ec910..bd76fe148a7 100644 --- a/icu4c/source/i18n/anytrans.cpp +++ b/icu4c/source/i18n/anytrans.cpp @@ -182,7 +182,7 @@ AnyTransliterator::AnyTransliterator(const UnicodeString& id, Transliterator(id, NULL), targetScript(theTargetScript) { - cache = uhash_open(uhash_hashLong, uhash_compareLong, &ec); + cache = uhash_open(uhash_hashLong, uhash_compareLong, NULL, &ec); uhash_setValueDeleter(cache, _deleteTransliterator); target = theTarget; @@ -205,7 +205,7 @@ AnyTransliterator::AnyTransliterator(const AnyTransliterator& o) : { // Don't copy the cache contents UErrorCode ec = U_ZERO_ERROR; - cache = uhash_open(uhash_hashLong, uhash_compareLong, &ec); + cache = uhash_open(uhash_hashLong, uhash_compareLong, NULL, &ec); uhash_setValueDeleter(cache, _deleteTransliterator); } diff --git a/icu4c/source/i18n/astro.cpp b/icu4c/source/i18n/astro.cpp index 1b36332d6c2..e7ee98220ad 100644 --- a/icu4c/source/i18n/astro.cpp +++ b/icu4c/source/i18n/astro.cpp @@ -1543,7 +1543,7 @@ void CalendarCache::put(CalendarCache** cache, int32_t key, int32_t value, UErro } CalendarCache::CalendarCache(int32_t size, UErrorCode &status) { - fTable = uhash_openSize(uhash_hashLong, uhash_compareLong, size, &status); + fTable = uhash_openSize(uhash_hashLong, uhash_compareLong, NULL, size, &status); U_DEBUG_ASTRO_MSG(("%p: Opening.\n", fTable)); } diff --git a/icu4c/source/i18n/dtfmtsym.cpp b/icu4c/source/i18n/dtfmtsym.cpp index f694789ff64..3e5af4dc99b 100644 --- a/icu4c/source/i18n/dtfmtsym.cpp +++ b/icu4c/source/i18n/dtfmtsym.cpp @@ -435,27 +435,15 @@ DateFormatSymbols::operator==(const DateFormatSymbols& other) const return FALSE; } }else{ - if(hashCompare(fZoneStringsHash, other.fZoneStringsHash) == FALSE){ + if(fZoneStringsHash->equals(*other.fZoneStringsHash) == FALSE){ return FALSE; } // we always make sure that we update the enumeration when the hash is // updated. So we can be sure that once we compare the hashes the // enumerations are also equal - //if(stringEnumCompare(fZoneIDEnumeration, other.fZoneIDEnumeration)==FALSE){ - // return FALSE; - //} } // since fZoneStrings data member is deprecated .. and may not be initialized // so don't compare them - // fZoneStringsRowCount == other.fZoneStringsRowCount && - //fZoneStringsColCount == other.fZoneStringsColCount - //if (fZoneStrings == other.fZoneStrings) return TRUE; - // - //for (int32_t row=0; rowcount(status); fZoneStringsColCount = 8; fZoneStrings = (UnicodeString **)uprv_malloc(fZoneStringsRowCount * sizeof(UnicodeString *)); - /* test for NULL */ - if (fZoneStrings == 0) { + /* if we can't get a chunk of heap then the system is going down. Pin the blame on system*/ + if (fZoneStrings == NULL) { status = U_MEMORY_ALLOCATION_ERROR; return; } @@ -1365,6 +1389,25 @@ DateFormatSymbols::initZoneStringsArray(UErrorCode& status){ } } +UBool U_CALLCONV +uhash_compareTZHashValues(const UHashTok val1, const UHashTok val2){ + + const UnicodeString* array1 = (UnicodeString*) val1.pointer; + const UnicodeString* array2 = (UnicodeString*) val2.pointer; + if(array1==array2){ + return TRUE; + } + if(array1==NULL || array2==NULL){ + return FALSE; + } + for(int32_t j=0; j< UTZ_MAX_DISPLAY_STRINGS_LENGTH; j++){ + if(array1[j] != array2[j]){ + return FALSE; + } + } + return TRUE; +} + void DateFormatSymbols::initZoneStrings(UErrorCode &status){ if(U_FAILURE(status)){ @@ -1376,7 +1419,7 @@ DateFormatSymbols::initZoneStrings(UErrorCode &status){ } int32_t i; - fZoneStringsHash = new Hashtable(status); + fZoneStringsHash = new Hashtable(uhash_compareUnicodeString, uhash_compareTZHashValues, status); if(fZoneStringsHash==NULL){ status = U_MEMORY_ALLOCATION_ERROR; return; @@ -1495,12 +1538,7 @@ DateFormatSymbols::initZoneStrings(UErrorCode &status){ } } void -DateFormatSymbols::initZoneStrings(const UnicodeString** strings, int32_t rowCount, int32_t columnCount){ - // This method should have a status parameter - // but setZoneStrings API that calls this method does not have one - // setZoneStrings API is unsafe and should be deprecated!! - UErrorCode status = U_ZERO_ERROR; - +DateFormatSymbols::initZoneStrings(const UnicodeString** strings, int32_t rowCount, int32_t columnCount, UErrorCode& status){ if(strings==NULL || rowCount<0 || columnCount<0){ status = U_ILLEGAL_ARGUMENT_ERROR; return; @@ -1514,7 +1552,7 @@ DateFormatSymbols::initZoneStrings(const UnicodeString** strings, int32_t rowCou status = U_MEMORY_ALLOCATION_ERROR; return; } - fZoneStringsHash = new Hashtable(status); + fZoneStringsHash = new Hashtable(uhash_compareUnicodeString, uhash_compareTZHashValues, status); if(U_FAILURE(status)){ return; } @@ -1637,7 +1675,7 @@ DateFormatSymbols::setZoneString(const UnicodeString &zid, const TimeZoneTransla Hashtable* DateFormatSymbols::createZoneStringsHash(const Hashtable* otherHash){ UErrorCode status = U_ZERO_ERROR; - Hashtable* hash = new Hashtable(status); + Hashtable* hash = new Hashtable(uhash_compareUnicodeString, uhash_compareTZHashValues, status); if(hash==NULL){ return NULL; } @@ -1669,76 +1707,7 @@ DateFormatSymbols::createZoneStringsHash(const Hashtable* otherHash){ return hash; } -/** - * compares 2 StringEnumerations - */ -UBool -DateFormatSymbols::stringEnumCompare(StringEnumeration* e1, - StringEnumeration* e2){ - TimeZoneKeysEnumeration *enum1 = (TimeZoneKeysEnumeration*)e1; - TimeZoneKeysEnumeration *enum2 = (TimeZoneKeysEnumeration*)e2; - if(enum1==NULL || enum2==NULL){ - return FALSE; - } - - UErrorCode status = U_ZERO_ERROR; - int32_t count1 = enum1->count(status); - int32_t count2 = enum2->count(status); - if(count1 != count2){ - return FALSE; - } - int32_t pos1 = 0; - int32_t pos2 = 0; - const UnicodeString* str1 = NULL; - const UnicodeString* str2 = NULL; - - while((str1 = enum1->snext(pos1, status))!=NULL){ - str2 = enum2->snext(pos2, status); - if(U_FAILURE(status)){ - return FALSE; - } - if(*str1 != *str2){ - // bail out at the first failure - return FALSE; - } - - } - // if we reached here that means that the enumerations are equal - return TRUE; -} -/** - * compares 2 Hashtables - */ -UBool -DateFormatSymbols::hashCompare(Hashtable* hash1, - Hashtable* hash2){ - - if(hash1==NULL || hash2==NULL){ - return FALSE; - } - int32_t count1 = hash1->count(); - int32_t count2 = hash2->count(); - if(count1!=count2){ - return FALSE; - } - int32_t pos1=-1; - for(int32_t i=0; inextElement(pos1); - UnicodeString* key1 = (UnicodeString*) elem1->key.pointer; - UnicodeString* array1 = (UnicodeString*) elem1->value.pointer; - UnicodeString* array2 = (UnicodeString*)hash2->get(*key1); - if(array1==NULL || array2==NULL){ - return FALSE; - } - for(int32_t j=0; j< UTZ_MAX_DISPLAY_STRINGS_LENGTH; j++){ - if(array1[j] != array2[j]){ - return FALSE; - } - } - } - return TRUE; -} UnicodeString& DateFormatSymbols::getZoneID(const UnicodeString& zid, UnicodeString& result, UErrorCode& status){ if(fZoneStringsHash == NULL){ diff --git a/icu4c/source/i18n/olsontz.cpp b/icu4c/source/i18n/olsontz.cpp index 19d3f2c59e6..ccddacb9314 100644 --- a/icu4c/source/i18n/olsontz.cpp +++ b/icu4c/source/i18n/olsontz.cpp @@ -478,13 +478,7 @@ OlsonTimeZone::getDSTSavings() const{ if(finalZone!=NULL){ return finalZone->getDSTSavings(); } - // return super->getDSTSavings(); - // this is basically identical to implementation in - // superclass timezone - if (useDaylightTime()) { - return 3600000; - } - return 0; + return TimeZone::getDSTSavings(); } /** * TimeZone API. diff --git a/icu4c/source/i18n/smpdtfmt.cpp b/icu4c/source/i18n/smpdtfmt.cpp index f1fc9f825b1..c297eedf3f6 100644 --- a/icu4c/source/i18n/smpdtfmt.cpp +++ b/icu4c/source/i18n/smpdtfmt.cpp @@ -384,15 +384,6 @@ SimpleDateFormat::initialize(const Locale& locale, { if (U_FAILURE(status)) return; - // {sfb} should this be here? - /* - commenting this code out check for bogus locale data does not belong here - if (fSymbols->fZoneStringsColCount < 1) - { - status = U_INVALID_FORMAT_ERROR; // Check for bogus locale data - return; - } - */ // We don't need to check that the row count is >= 1, since all 2d arrays have at // least one row fNumberFormat = NumberFormat::createInstance(locale, status); @@ -1557,47 +1548,7 @@ int32_t SimpleDateFormat::subParse(const UnicodeString& text, int32_t& start, UC return -start; } } -/* -int32_t -SimpleDateFormat::getTimeZoneIndex(const UnicodeString& id) const -{ - int32_t i = fSymbols->fZoneStringsRowCount; - while (--i >= 0 && fSymbols->fZoneStrings[i][0] != id); - return i; -} -int32_t -SimpleDateFormat::matchZoneString(const UnicodeString& text, int32_t start, int32_t zi) const -{ - // ### TODO markus 20021014: This use of caseCompare() will fail - // if the text contains a character that case-folds into multiple - // characters. In that case, zs->length() may be too long, and it does not match. - // We need a case-insensitive version of startsWith(). - // There are similar cases of such caseCompare() uses elsewhere in ICU. - - int32_t i = fSymbols->fZoneStringsColCount; - const int32_t zscc = i; - - while (--i >= 1) { - if (i == 5 && (zscc == 6 || zscc >= 8)) { // skip city name if we have it - continue; - } - - // Checking long and short zones [1 & 2], - // and long and short daylight [3 & 4], - // and long and short generic [6 & 7] - const UnicodeString& zs = fSymbols->fZoneStrings[zi][i]; - if (zs.length() > 0 && 0 == text.caseCompare(start, zs.length(), zs, 0)) { - break; - } - } - return i; -} -*/ -/** - * find time zone 'text' matched zoneStrings and set cal. - * includes optimizations for calendar and default time zones - */ int32_t SimpleDateFormat::subParseZoneString(const UnicodeString& text, int32_t start, Calendar& cal, UErrorCode& status) const { diff --git a/icu4c/source/i18n/ucol_elm.cpp b/icu4c/source/i18n/ucol_elm.cpp index b5d400fb03a..2c61f63bf7b 100644 --- a/icu4c/source/i18n/ucol_elm.cpp +++ b/icu4c/source/i18n/ucol_elm.cpp @@ -151,7 +151,7 @@ uprv_uca_initTempTable(UCATableHeader *image, UColOptionSet *opts, const UCollat UCOL_SPECIAL_FLAG | (initTag<<24), UCOL_SPECIAL_FLAG | (supplementaryInitTag << 24), TRUE); // Do your own mallocs for the structure, array and have linear Latin 1 - t->prefixLookup = uhash_open(prefixLookupHash, prefixLookupComp, status); + t->prefixLookup = uhash_open(prefixLookupHash, prefixLookupComp, NULL, status); uhash_setValueDeleter(t->prefixLookup, uhash_freeBlock); t->contractions = uprv_cnttab_open(t->mapping, status); diff --git a/icu4c/source/i18n/ucol_tok.cpp b/icu4c/source/i18n/ucol_tok.cpp index 92038b936ef..3956d5dc535 100644 --- a/icu4c/source/i18n/ucol_tok.cpp +++ b/icu4c/source/i18n/ucol_tok.cpp @@ -1820,7 +1820,7 @@ void ucol_tok_initTokenList(UColTokenParser *src, const UChar *rules, const uint if(U_FAILURE(*status)) { return; } - src->tailored = uhash_open(uhash_hashTokens, uhash_compareTokens, status); + src->tailored = uhash_open(uhash_hashTokens, uhash_compareTokens, NULL, status); if(U_FAILURE(*status)) { return; } diff --git a/icu4c/source/i18n/unicode/dtfmtsym.h b/icu4c/source/i18n/unicode/dtfmtsym.h index c134714ed03..530b077f07e 100644 --- a/icu4c/source/i18n/unicode/dtfmtsym.h +++ b/icu4c/source/i18n/unicode/dtfmtsym.h @@ -668,7 +668,7 @@ private: * initialzes the zoneStrings has and keys enumeration after reading the strings[][]. Required for backwards * compatibility of setZoneStrings method */ - void initZoneStrings(const UnicodeString** strings, int32_t rowCount, int32_t collumnCount); + void initZoneStrings(const UnicodeString** strings, int32_t rowCount, int32_t collumnCount, UErrorCode& status); /** * initialization of the fZoneStrings data member */ @@ -677,15 +677,7 @@ private: * Creates a deep clone of the Hashtable */ Hashtable* createZoneStringsHash(const Hashtable* otherHash); - /** - * compares 2 StringEnumerations - */ - static UBool stringEnumCompare(StringEnumeration* enum1, StringEnumeration* enum2); - /** - * compares 2 Hashtables - */ - static UBool hashCompare(Hashtable* hash1, Hashtable* hash2); - + /** * Fetches the key from the hashtable for a given ID. * e.g: for a given ID such as PST returns "Americal/Los_Angeles" diff --git a/icu4c/source/i18n/unicode/smpdtfmt.h b/icu4c/source/i18n/unicode/smpdtfmt.h index ea6dc0d3fa3..c5105844ff2 100644 --- a/icu4c/source/i18n/unicode/smpdtfmt.h +++ b/icu4c/source/i18n/unicode/smpdtfmt.h @@ -772,12 +772,6 @@ private: */ void parseAmbiguousDatesAsAfter(UDate startDate, UErrorCode& status); - /** - * Given a canonical time zone id, return the row index in our symbols for that id, - * or -1 if none found. - * - int32_t getTimeZoneIndex(const UnicodeString& id) const; - */ /** * Given text, a start in the text, and a row index, return the column index that * of the zone name that matches (case insensitive) at start, or 0 if none matches. diff --git a/icu4c/source/test/cintltst/chashtst.c b/icu4c/source/test/cintltst/chashtst.c index 8dd66b45189..c70ae2bca5d 100644 --- a/icu4c/source/test/cintltst/chashtst.c +++ b/icu4c/source/test/cintltst/chashtst.c @@ -1,6 +1,6 @@ /* ******************************************************************************* -* Copyright (C) 2000-2004, International Business Machines +* Copyright (C) 2000-2005, International Business Machines * Corporation and others. All Rights Reserved. ******************************************************************************* * Date Name Description @@ -103,7 +103,7 @@ static void TestBasic(void) { UErrorCode status = U_ZERO_ERROR; UHashtable *hash; - hash = uhash_open(hashChars, isEqualChars, &status); + hash = uhash_open(hashChars, isEqualChars, NULL, &status); if (U_FAILURE(status)) { log_err("FAIL: uhash_open failed with %s and returned 0x%08x\n", u_errorName(status), hash); @@ -163,7 +163,7 @@ static void TestOtherAPI(void){ static const UChar five[6] = {0x0066, 0x0069, 0x0076, 0x0065, 0}; /* L"five" */ static const UChar five2[6] = {0x0066, 0x0069, 0x0076, 0x0065, 0}; /* L"five" */ - hash = uhash_open(uhash_hashUChars, uhash_compareUChars, &status); + hash = uhash_open(uhash_hashUChars, uhash_compareUChars, NULL, &status); if (U_FAILURE(status)) { log_err("FAIL: uhash_open failed with %s and returned 0x%08x\n", u_errorName(status), hash); @@ -287,7 +287,7 @@ static void hashIChars(void) { UErrorCode status = U_ZERO_ERROR; UHashtable *hash; - hash = uhash_open(uhash_hashIChars, uhash_compareIChars, &status); + hash = uhash_open(uhash_hashIChars, uhash_compareIChars, NULL, &status); if (U_FAILURE(status)) { log_err("FAIL: uhash_open failed with %s and returned 0x%08x\n", u_errorName(status), hash); diff --git a/icu4c/source/test/intltest/dtfmttst.cpp b/icu4c/source/test/intltest/dtfmttst.cpp index a1d94e5cdc1..8a3cfc64d3f 100644 --- a/icu4c/source/test/intltest/dtfmttst.cpp +++ b/icu4c/source/test/intltest/dtfmttst.cpp @@ -1515,6 +1515,11 @@ void DateFormatTest::TestTimeZoneStringsAPI() { errln("Could not create the StringEnumeration for Locale::getUS(). Error: %s", u_errorName(status)); return; } + + StringEnumeration* keys2 = symbols.createZoneStringIDs(status); + if(*keys2!=*keys){ + errln("operator!= failed for TimeZoneStringsEnum"); + } const UnicodeString* key = NULL; while( (key = keys->snext(status))!=NULL){ diff --git a/icu4c/source/test/intltest/tsdtfmsy.cpp b/icu4c/source/test/intltest/tsdtfmsy.cpp index 44203067410..ff080b1a31c 100644 --- a/icu4c/source/test/intltest/tsdtfmsy.cpp +++ b/icu4c/source/test/intltest/tsdtfmsy.cpp @@ -305,8 +305,11 @@ void IntlTestDateFormatSymbols::TestSymbols(/* char *par */) en = fr; - if(en != fr || foo != bar) { - errln("ERROR: Copy Constructor or Assignment failed"); + if(en != fr) { + errln("ERROR: Assignment operator failed"); + } + if(foo != bar) { + errln("ERROR: Copy Constructor failed"); } } diff --git a/icu4c/source/tools/gensprep/store.c b/icu4c/source/tools/gensprep/store.c index 60b70ec5e1a..ee9d68b99e9 100644 --- a/icu4c/source/tools/gensprep/store.c +++ b/icu4c/source/tools/gensprep/store.c @@ -377,7 +377,7 @@ storeMapping(uint32_t codepoint, uint32_t* mapping,int32_t length, /* initialize the hashtable */ if(hashTable==NULL){ - hashTable = uhash_open(hashEntry, compareEntries, status); + hashTable = uhash_open(hashEntry, compareEntries, NULL, status); uhash_setValueDeleter(hashTable, valueDeleter); }