mirror of
https://github.com/unicode-org/icu.git
synced 2025-04-21 12:40:02 +00:00
X-SVN-Rev: 30352
This commit is contained in:
parent
b5f6a9af3c
commit
a1b3ab982e
7 changed files with 128 additions and 29 deletions
|
@ -976,7 +976,7 @@ static UResourceBundle *init_resb_result(const ResourceData *rdata, Resource r,
|
|||
} else if(idx != -1) {
|
||||
/* if there is no key, but there is an index, try to get by the index */
|
||||
/* here we have either a table or an array, so get the element */
|
||||
UResType type = RES_GET_TYPE(r);
|
||||
int32_t type = RES_GET_TYPE(r);
|
||||
if(URES_IS_TABLE(type)) {
|
||||
r = res_getTableItemByIndex(&(mainRes->fResData), r, idx, (const char **)&aKey);
|
||||
} else { /* array */
|
||||
|
@ -1685,7 +1685,6 @@ ures_getByKeyWithFallback(const UResourceBundle *resB,
|
|||
/*UResourceDataEntry *realData = NULL;*/
|
||||
const char *key = inKey;
|
||||
UResourceBundle *helper = NULL;
|
||||
UResType type;
|
||||
|
||||
if (status==NULL || U_FAILURE(*status)) {
|
||||
return fillIn;
|
||||
|
@ -1695,7 +1694,7 @@ ures_getByKeyWithFallback(const UResourceBundle *resB,
|
|||
return fillIn;
|
||||
}
|
||||
|
||||
type = RES_GET_TYPE(resB->fRes);
|
||||
int32_t type = RES_GET_TYPE(resB->fRes);
|
||||
if(URES_IS_TABLE(type)) {
|
||||
int32_t t;
|
||||
res = res_getTableItemByKey(&(resB->fResData), resB->fRes, &t, &key);
|
||||
|
@ -1763,7 +1762,6 @@ U_CAPI UResourceBundle* U_EXPORT2 ures_getByKey(const UResourceBundle *resB, con
|
|||
Resource res = RES_BOGUS;
|
||||
UResourceDataEntry *realData = NULL;
|
||||
const char *key = inKey;
|
||||
UResType type;
|
||||
|
||||
if (status==NULL || U_FAILURE(*status)) {
|
||||
return fillIn;
|
||||
|
@ -1773,7 +1771,7 @@ U_CAPI UResourceBundle* U_EXPORT2 ures_getByKey(const UResourceBundle *resB, con
|
|||
return fillIn;
|
||||
}
|
||||
|
||||
type = RES_GET_TYPE(resB->fRes);
|
||||
int32_t type = RES_GET_TYPE(resB->fRes);
|
||||
if(URES_IS_TABLE(type)) {
|
||||
int32_t t;
|
||||
res = res_getTableItemByKey(&(resB->fResData), resB->fRes, &t, &key);
|
||||
|
@ -1817,7 +1815,6 @@ U_CAPI const UChar* U_EXPORT2 ures_getStringByKey(const UResourceBundle *resB, c
|
|||
Resource res = RES_BOGUS;
|
||||
UResourceDataEntry *realData = NULL;
|
||||
const char* key = inKey;
|
||||
UResType type;
|
||||
|
||||
if (status==NULL || U_FAILURE(*status)) {
|
||||
return NULL;
|
||||
|
@ -1827,7 +1824,7 @@ U_CAPI const UChar* U_EXPORT2 ures_getStringByKey(const UResourceBundle *resB, c
|
|||
return NULL;
|
||||
}
|
||||
|
||||
type = RES_GET_TYPE(resB->fRes);
|
||||
int32_t type = RES_GET_TYPE(resB->fRes);
|
||||
if(URES_IS_TABLE(type)) {
|
||||
int32_t t=0;
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
/*
|
||||
******************************************************************************
|
||||
* *
|
||||
* Copyright (C) 1999-2009, International Business Machines *
|
||||
* Copyright (C) 1999-2011, International Business Machines *
|
||||
* Corporation and others. All Rights Reserved. *
|
||||
* *
|
||||
******************************************************************************
|
||||
|
@ -61,7 +61,7 @@ typedef uint32_t Resource;
|
|||
|
||||
#define RES_BOGUS 0xffffffff
|
||||
|
||||
#define RES_GET_TYPE(res) ((UResType)((res)>>28UL))
|
||||
#define RES_GET_TYPE(res) ((int32_t)((res)>>28UL))
|
||||
#define RES_GET_OFFSET(res) ((res)&0x0fffffff)
|
||||
#define RES_GET_POINTER(pRoot, res) ((pRoot)+RES_GET_OFFSET(res))
|
||||
|
||||
|
@ -69,8 +69,8 @@ typedef uint32_t Resource;
|
|||
#define RES_GET_INT(res) (((int32_t)((res)<<4L))>>4L)
|
||||
#define RES_GET_UINT(res) ((res)&0x0fffffff)
|
||||
|
||||
#define URES_IS_ARRAY(type) ((type)==URES_ARRAY || (type)==URES_ARRAY16)
|
||||
#define URES_IS_TABLE(type) ((type)==URES_TABLE || (type)==URES_TABLE16 || (type)==URES_TABLE32)
|
||||
#define URES_IS_ARRAY(type) ((int32_t)(type)==URES_ARRAY || (int32_t)(type)==URES_ARRAY16)
|
||||
#define URES_IS_TABLE(type) ((int32_t)(type)==URES_TABLE || (int32_t)(type)==URES_TABLE16 || (int32_t)(type)==URES_TABLE32)
|
||||
#define URES_IS_CONTAINER(type) (URES_IS_TABLE(type) || URES_IS_ARRAY(type))
|
||||
|
||||
#define URES_MAKE_RESOURCE(type, offset) (((Resource)(type)<<28)|(Resource)(offset))
|
||||
|
|
|
@ -31,7 +31,7 @@
|
|||
#include "uhash.h"
|
||||
#include "uvector.h"
|
||||
|
||||
#include <string>
|
||||
//#include <string>
|
||||
#include <iostream>
|
||||
U_NAMESPACE_BEGIN
|
||||
|
||||
|
|
|
@ -39,6 +39,7 @@ public:
|
|||
UnicodeString& tzID, UTimeZoneTimeType* timeType = NULL) const;
|
||||
|
||||
private:
|
||||
UMTX fLock;
|
||||
Locale fLocale;
|
||||
char fTargetRegion[ULOC_COUNTRY_CAPACITY];
|
||||
TimeZoneNames* fTimeZoneNames;
|
||||
|
@ -48,10 +49,12 @@ private:
|
|||
|
||||
UnicodeString& formatSpecific(const TimeZone& tz, UTimeZoneNameType stdType, UTimeZoneNameType dstType,
|
||||
UDate date, UnicodeString& name, UTimeZoneTimeType *timeType) const;
|
||||
|
||||
const TimeZoneGenericNames* getTimeZoneGenericNames(UErrorCode& status) const;
|
||||
};
|
||||
|
||||
TimeZoneFormatImpl::TimeZoneFormatImpl(const Locale& locale, UErrorCode& status)
|
||||
: fLocale(locale), fTimeZoneNames(NULL), fTimeZoneGenericNames(NULL) {
|
||||
: fLocale(locale), fTimeZoneNames(NULL), fTimeZoneGenericNames(NULL), fLock(NULL) {
|
||||
|
||||
const char* region = fLocale.getCountry();
|
||||
int32_t regionLen = uprv_strlen(region);
|
||||
|
@ -72,10 +75,7 @@ TimeZoneFormatImpl::TimeZoneFormatImpl(const Locale& locale, UErrorCode& status)
|
|||
}
|
||||
|
||||
fTimeZoneNames = TimeZoneNames::createInstance(locale, status);
|
||||
fTimeZoneGenericNames = new TimeZoneGenericNames(locale, status);
|
||||
if (U_SUCCESS(status) && fTimeZoneGenericNames == NULL) {
|
||||
status = U_MEMORY_ALLOCATION_ERROR;
|
||||
}
|
||||
// fTimeZoneGenericNames is lazily instantiated
|
||||
}
|
||||
|
||||
TimeZoneFormatImpl::~TimeZoneFormatImpl() {
|
||||
|
@ -85,6 +85,7 @@ TimeZoneFormatImpl::~TimeZoneFormatImpl() {
|
|||
if (fTimeZoneGenericNames != NULL) {
|
||||
delete fTimeZoneGenericNames;
|
||||
}
|
||||
umtx_destroy(&fLock);
|
||||
}
|
||||
|
||||
const TimeZoneNames*
|
||||
|
@ -92,6 +93,31 @@ TimeZoneFormatImpl::getTimeZoneNames() const {
|
|||
return fTimeZoneNames;
|
||||
}
|
||||
|
||||
const TimeZoneGenericNames*
|
||||
TimeZoneFormatImpl::getTimeZoneGenericNames(UErrorCode& status) const {
|
||||
if (U_FAILURE(status)) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
UBool create;
|
||||
UMTX_CHECK(&gZoneMetaLock, (fTimeZoneGenericNames == NULL), create);
|
||||
if (create) {
|
||||
TimeZoneFormatImpl *nonConstThis = const_cast<TimeZoneFormatImpl *>(this);
|
||||
umtx_lock(&nonConstThis->fLock);
|
||||
{
|
||||
if (fTimeZoneGenericNames == NULL) {
|
||||
nonConstThis->fTimeZoneGenericNames = new TimeZoneGenericNames(fLocale, status);
|
||||
if (U_SUCCESS(status) && fTimeZoneGenericNames == NULL) {
|
||||
status = U_MEMORY_ALLOCATION_ERROR;
|
||||
}
|
||||
}
|
||||
}
|
||||
umtx_unlock(&nonConstThis->fLock);
|
||||
}
|
||||
|
||||
return fTimeZoneGenericNames;
|
||||
}
|
||||
|
||||
UnicodeString&
|
||||
TimeZoneFormatImpl::format(UTimeZoneFormatStyle style, const TimeZone& tz, UDate date,
|
||||
UnicodeString& name, UTimeZoneTimeType* timeType /* = NULL */) const {
|
||||
|
@ -163,7 +189,11 @@ TimeZoneFormatImpl::parse(UTimeZoneFormatStyle style, const UnicodeString& text,
|
|||
UErrorCode status = U_ZERO_ERROR;
|
||||
|
||||
if (isGeneric) {
|
||||
int32_t len = fTimeZoneGenericNames->findBestMatch(text, startIdx, types, parsedTzID, parsedTimeType, status);
|
||||
int32_t len = 0;
|
||||
const TimeZoneGenericNames *gnames = getTimeZoneGenericNames(status);
|
||||
if (U_SUCCESS(status)) {
|
||||
len = gnames->findBestMatch(text, startIdx, types, parsedTzID, parsedTimeType, status);
|
||||
}
|
||||
if (U_FAILURE(status) || len == 0) {
|
||||
pos.setErrorIndex(startIdx);
|
||||
return tzID;
|
||||
|
@ -221,7 +251,9 @@ TimeZoneFormatImpl::parse(UTimeZoneFormatStyle style, const UnicodeString& text,
|
|||
|
||||
UnicodeString&
|
||||
TimeZoneFormatImpl::formatGeneric(const TimeZone& tz, UTimeZoneGenericNameType genType, UDate date, UnicodeString& name) const {
|
||||
if (fTimeZoneGenericNames == NULL) {
|
||||
UErrorCode status = U_ZERO_ERROR;
|
||||
const TimeZoneGenericNames* gnames = getTimeZoneGenericNames(status);
|
||||
if (U_FAILURE(status)) {
|
||||
name.setToBogus();
|
||||
return name;
|
||||
}
|
||||
|
@ -232,9 +264,9 @@ TimeZoneFormatImpl::formatGeneric(const TimeZone& tz, UTimeZoneGenericNameType g
|
|||
name.setToBogus();
|
||||
return name;
|
||||
}
|
||||
return fTimeZoneGenericNames->getGenericLocationName(UnicodeString(canonicalID), name);
|
||||
return gnames->getGenericLocationName(UnicodeString(canonicalID), name);
|
||||
}
|
||||
return fTimeZoneGenericNames->getDisplayName(tz, genType, date, name);
|
||||
return gnames->getDisplayName(tz, genType, date, name);
|
||||
}
|
||||
|
||||
UnicodeString&
|
||||
|
|
|
@ -6417,7 +6417,7 @@ void ucol_updateInternalState(UCollator *coll, UErrorCode *status) {
|
|||
}
|
||||
|
||||
/* Set the compression values */
|
||||
uint8_t tertiaryTotal = (uint8_t)(coll->tertiaryTop - UCOL_COMMON_BOT3-1);
|
||||
uint8_t tertiaryTotal = (uint8_t)(coll->tertiaryTop - coll->tertiaryBottom - 1);
|
||||
coll->tertiaryTopCount = (uint8_t)(UCOL_PROPORTION3*tertiaryTotal); /* we multilply double with int, but need only int */
|
||||
coll->tertiaryBottomCount = (uint8_t)(tertiaryTotal - coll->tertiaryTopCount);
|
||||
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/********************************************************************
|
||||
* COPYRIGHT:
|
||||
* Copyright (c) 1997-2010, International Business Machines Corporation and
|
||||
* Copyright (c) 1997-2011, International Business Machines Corporation and
|
||||
* others. All Rights Reserved.
|
||||
********************************************************************/
|
||||
|
||||
|
@ -1157,6 +1157,67 @@ void CollationRegressionTest::TestT7189() {
|
|||
ucol_close(coll);
|
||||
}
|
||||
|
||||
void CollationRegressionTest::TestCaseFirstCompression() {
|
||||
RuleBasedCollator *col = (RuleBasedCollator *) en_us->clone();
|
||||
UErrorCode status = U_ZERO_ERROR;
|
||||
|
||||
// default
|
||||
caseFirstCompressionSub(col, "default");
|
||||
|
||||
// Upper first
|
||||
col->setAttribute(UCOL_CASE_FIRST, UCOL_UPPER_FIRST, status);
|
||||
if (U_FAILURE(status)) {
|
||||
errln("Failed to set UCOL_UPPER_FIRST");
|
||||
return;
|
||||
}
|
||||
caseFirstCompressionSub(col, "upper first");
|
||||
|
||||
// Lower first
|
||||
col->setAttribute(UCOL_CASE_FIRST, UCOL_LOWER_FIRST, status);
|
||||
if (U_FAILURE(status)) {
|
||||
errln("Failed to set UCOL_LOWER_FIRST");
|
||||
return;
|
||||
}
|
||||
caseFirstCompressionSub(col, "lower first");
|
||||
|
||||
delete col;
|
||||
}
|
||||
|
||||
void CollationRegressionTest::caseFirstCompressionSub(Collator *col, UnicodeString opt) {
|
||||
const int32_t maxLength = 50;
|
||||
|
||||
UChar str1[maxLength];
|
||||
UChar str2[maxLength];
|
||||
|
||||
CollationKey key1, key2;
|
||||
|
||||
for (int32_t len = 1; len <= maxLength; len++) {
|
||||
int32_t i = 0;
|
||||
for (; i < len - 1; i++) {
|
||||
str1[i] = str2[i] = (UChar)0x61; // 'a'
|
||||
}
|
||||
str1[i] = (UChar)0x41; // 'A'
|
||||
str2[i] = (UChar)0x61; // 'a'
|
||||
|
||||
UErrorCode status = U_ZERO_ERROR;
|
||||
col->getCollationKey(str1, len, key1, status);
|
||||
col->getCollationKey(str2, len, key2, status);
|
||||
|
||||
UCollationResult cmpKey = key1.compareTo(key2, status);
|
||||
UCollationResult cmpCol = col->compare(str1, len, str2, len, status);
|
||||
|
||||
if (U_FAILURE(status)) {
|
||||
errln("Error in caseFirstCompressionSub");
|
||||
} else if (cmpKey != cmpCol) {
|
||||
errln((UnicodeString)"Inconsistent comparison(" + opt
|
||||
+ "): str1=" + UnicodeString(str1, len) + ", str2=" + UnicodeString(str2, len)
|
||||
+ ", cmpKey=" + cmpKey + ", cmpCol=" + cmpCol);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void CollationRegressionTest::compareArray(Collator &c,
|
||||
const UChar tests[][CollationRegressionTest::MAX_TOKEN_LEN],
|
||||
int32_t testCount)
|
||||
|
@ -1288,7 +1349,8 @@ void CollationRegressionTest::runIndexedTest(int32_t index, UBool exec, const ch
|
|||
case 28: name = "Test4139572"; if (exec) Test4139572(/* par */); break;
|
||||
case 29: name = "Test4141640"; if (exec) Test4141640(/* par */); break;
|
||||
case 30: name = "Test4146160"; if (exec) Test4146160(/* par */); break;
|
||||
case 31: name = "TestT7189"; if (exec) TestT7189(); break;
|
||||
case 31: name = "TestT7189"; if (exec) TestT7189(); break;
|
||||
case 32: name = "TestCaseFirstCompression"; if (exec) TestCaseFirstCompression(); break;
|
||||
default: name = ""; break;
|
||||
}
|
||||
} else {
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/********************************************************************
|
||||
* COPYRIGHT:
|
||||
* Copyright (c) 1997-2009, International Business Machines Corporation and
|
||||
* Copyright (c) 1997-2011, International Business Machines Corporation and
|
||||
* others. All Rights Reserved.
|
||||
********************************************************************/
|
||||
|
||||
|
@ -224,10 +224,17 @@ public:
|
|||
//
|
||||
void Test4146160(/* char* par */);
|
||||
|
||||
// Ticket 7189
|
||||
//
|
||||
// nextSortKeyPart incorrect for EO_S1 collation
|
||||
void TestT7189();
|
||||
// Ticket 7189
|
||||
//
|
||||
// nextSortKeyPart incorrect for EO_S1 collation
|
||||
//
|
||||
void TestT7189();
|
||||
|
||||
// Ticket 8624
|
||||
//
|
||||
// Tertiary value compression problem with case first option enabled
|
||||
//
|
||||
void TestCaseFirstCompression();
|
||||
|
||||
private:
|
||||
//------------------------------------------------------------------------
|
||||
|
@ -242,6 +249,7 @@ private:
|
|||
|
||||
RuleBasedCollator *en_us;
|
||||
|
||||
void caseFirstCompressionSub(Collator *col, UnicodeString opt);
|
||||
};
|
||||
|
||||
#endif /* #if !UCONFIG_NO_COLLATION */
|
||||
|
|
Loading…
Add table
Reference in a new issue