ICU-2347 add new timezone enumeration API and deprecate old one

X-SVN-Rev: 10230
This commit is contained in:
Alan Liu 2002-11-12 23:52:27 +00:00
parent 678e8ec99a
commit 66a285bef3
9 changed files with 429 additions and 76 deletions

View File

@ -48,6 +48,7 @@
#include "ucln_in.h"
#include "cstring.h"
#include "cmemory.h"
#include "unicode/strenum.h"
// static initialization
@ -459,6 +460,233 @@ TimeZone::setDefault(const TimeZone& zone)
// -------------------------------------
// New available IDs API as of ICU 2.4. Uses StringEnumeration API.
class TZEnumeration : public StringEnumeration {
// Map into to ZONE_IDS. Our results are ZONE_IDS[map[i]] for
// i=0..len-1. If map==NULL then our results are ZONE_IDS[i]
// for i=0..len-1. Len will be zero iff the zone data could
// not be loaded.
int32_t* map;
int32_t len;
int32_t pos;
void* _bufp;
int32_t _buflen;
enum { BUFFER_GROW = 8 }; // must be >= 1
public:
TZEnumeration() {
map = NULL;
_bufp = NULL;
len = pos = _buflen = 0;
if (!DATA_LOADED) {
loadZoneData();
}
if (DATA != NULL) {
len = DATA->count;
}
}
TZEnumeration(int32_t rawOffset) {
map = NULL;
_bufp = NULL;
len = pos = _buflen = 0;
if (!DATA_LOADED) {
loadZoneData();
}
if (DATA == NULL) return;
/* The offset index table is a table of variable-sized objects.
* Each entry has an offset to the next entry; the last entry has
* a next entry offset of zero.
*
* The entries are sorted in ascending numerical order of GMT
* offset. Each entry lists all the system zones at that offset,
* in lexicographic order of ID. Note that this ordering is
* somewhat significant in that the _first_ zone in each list is
* what will be chosen as the default under certain fallback
* conditions. We currently just let that be the
* lexicographically first zone, but we could also adjust the list
* to pick which zone was first for this situation -- probably not
* worth the trouble, except for the fact that this fallback is
* _always_ used to determine the default zone on Windows.
*
* The list of zones is actually just a list of integers, from
* 0..n-1, where n is the total number of system zones. The
* numbering corresponds exactly to the ordering of ZONE_IDS.
*/
const OffsetIndex* index = INDEX_BY_OFFSET;
for (;;) {
if (index->gmtOffset > rawOffset) {
// Went past our desired offset; no match found
break;
}
if (index->gmtOffset == rawOffset) {
// Found our desired offset
map = (int32_t*)uprv_malloc(sizeof(int32_t) * index->count);
if (map != NULL) {
len = index->count;
const uint16_t* zoneNumberArray = &(index->zoneNumber);
for (uint16_t i=0; i<len; ++i) {
map[i] = zoneNumberArray[i];
}
}
}
// Compute the position of the next entry. If the delta value
// in this entry is zero, then there is no next entry.
uint16_t delta = index->nextEntryDelta;
if (delta == 0) {
break;
}
index = (const OffsetIndex*)((int8_t*)index + delta);
}
}
TZEnumeration(const char* country) {
map = NULL;
_bufp = NULL;
len = pos = _buflen = 0;
if (!DATA_LOADED) {
loadZoneData();
}
if (DATA == NULL) return;
/* The country index table is a table of variable-sized objects.
* Each entry has an offset to the next entry; the last entry has
* a next entry offset of zero.
*
* The entries are sorted in ascending numerical order of intcode.
* This is an integer representation of the 2-letter ISO 3166
* country code. It is computed as (c1-'A')*32 + (c0-'A'), where
* the country code is c1 c0, with 'A' <= ci <= 'Z'.
*
* The list of zones is a list of integers, from 0..n-1, where n
* is the total number of system zones. The numbering corresponds
* exactly to the ordering of ZONE_IDS.
*/
const CountryIndex* index = INDEX_BY_COUNTRY;
uint16_t intcode = 0;
if (country != NULL && *country != 0) {
intcode = (uint16_t)((U_UPPER_ORDINAL(country[0]) << 5)
+ U_UPPER_ORDINAL(country[1]));
}
for (;;) {
if (index->intcode > intcode) {
// Went past our desired country; no match found
break;
}
if (index->intcode == intcode) {
// Found our desired country
map = (int32_t*)uprv_malloc(sizeof(int32_t) * index->count);
if (map != NULL) {
len = index->count;
const uint16_t* zoneNumberArray = &(index->zoneNumber);
for (uint16_t i=0; i<len; ++i) {
map[i] = zoneNumberArray[i];
}
}
}
// Compute the position of the next entry. If the delta value
// in this entry is zero, then there is no next entry.
uint16_t delta = index->nextEntryDelta;
if (delta == 0) {
break;
}
index = (const CountryIndex*)((int8_t*)index + delta);
}
}
virtual ~TZEnumeration() {
uprv_free(map);
uprv_free(_bufp);
}
int32_t count(UErrorCode& status) const {
return U_FAILURE(status) ? 0 : len;
}
const char* next(UErrorCode& status) {
const UnicodeString* us = snext(status);
if (us) {
int newlen;
for (newlen = us->extract((char*)_bufp, _buflen / sizeof(char), NULL, status);
status == U_STRING_NOT_TERMINATED_WARNING || status == U_BUFFER_OVERFLOW_ERROR;
) {
resizeBuffer((newlen + BUFFER_GROW) * sizeof(char));
status = U_ZERO_ERROR;
}
if (U_SUCCESS(status)) {
((char*)_bufp)[newlen] = 0;
return (const char*)_bufp;
}
}
return NULL;
}
const UChar* unext(UErrorCode& status) {
const UnicodeString* us = snext(status);
if (us) {
int newlen;
for (newlen = us->extract((UChar*)_bufp, _buflen / sizeof(UChar), status);
status == U_STRING_NOT_TERMINATED_WARNING || status == U_BUFFER_OVERFLOW_ERROR;
) {
resizeBuffer((newlen + BUFFER_GROW) * sizeof(UChar));
status = U_ZERO_ERROR;
}
if (U_SUCCESS(status)) {
((UChar*)_bufp)[newlen] = 0;
return (const UChar*)_bufp;
}
}
return NULL;
}
const UnicodeString* snext(UErrorCode& status) {
if (U_SUCCESS(status) && pos < len) {
return (map != NULL) ?
&ZONE_IDS[map[pos++]] : &ZONE_IDS[pos++];
}
return NULL;
}
void reset(UErrorCode& status) {
pos = 0;
}
private:
void resizeBuffer(int32_t newlen) {
if (_bufp) {
_bufp = uprv_realloc(_bufp, newlen);
} else {
_bufp = uprv_malloc(newlen);
}
_buflen = newlen;
}
};
StringEnumeration*
TimeZone::createEnumeration() {
return new TZEnumeration();
}
StringEnumeration*
TimeZone::createEnumeration(int32_t rawOffset) {
return new TZEnumeration(rawOffset);
}
StringEnumeration*
TimeZone::createEnumeration(const char* country) {
return new TZEnumeration(country);
}
// -------------------------------------
// TODO: #ifdef out this code after 8-Nov-2003
// #ifdef ICU_TIMEZONE_USE_DEPRECATES
const UnicodeString**
TimeZone::createAvailableIDs(int32_t rawOffset, int32_t& numIDs)
{
@ -631,6 +859,10 @@ TimeZone::createAvailableIDs(int32_t& numIDs)
return result;
}
// ICU_TIMEZONE_USE_DEPRECATES
// #endif
// see above
// ---------------------------------------
int32_t

View File

@ -14,10 +14,17 @@
#include "unicode/calendar.h"
#include "unicode/timezone.h"
#include "unicode/ustring.h"
#include "unicode/strenum.h"
#include "cmemory.h"
#include "ustrenum.h"
U_NAMESPACE_USE
U_CAPI UEnumeration* U_EXPORT2
ucal_openTimeZoneEnumeration(int32_t rawOffset, UErrorCode* ec) {
return uenum_openStringEnumeration(TimeZone::createEnumeration(rawOffset), ec);
}
U_CAPI const UChar* U_EXPORT2
ucal_getAvailableTZIDs( int32_t rawOffset,
int32_t index,
@ -26,22 +33,26 @@ ucal_getAvailableTZIDs( int32_t rawOffset,
if(U_FAILURE(*status)) return 0;
int32_t count = 0;
const UChar *retVal = 0;
const UnicodeString** tzs = TimeZone::createAvailableIDs(rawOffset,
count);
StringEnumeration* tzs = TimeZone::createEnumeration(rawOffset);
if(tzs == 0) {
*status = U_MEMORY_ALLOCATION_ERROR;
return 0;
}
if(index < count)
retVal = tzs[index]->getBuffer();
else
UErrorCode ec = U_ZERO_ERROR;
if (index >= 0 && index < tzs->count(ec)) {
for (;;) {
retVal = tzs->unext(ec);
if (U_FAILURE(ec) || retVal==NULL) {
break;
}
if (index-- == 0) break;
}
} else {
*status = U_INDEX_OUTOFBOUNDS_ERROR;
}
uprv_free(tzs);
return retVal;
}
@ -49,18 +60,14 @@ ucal_getAvailableTZIDs( int32_t rawOffset,
U_CAPI int32_t U_EXPORT2
ucal_countAvailableTZIDs(int32_t rawOffset)
{
int32_t count = 0;
const UnicodeString** tzs = TimeZone::createAvailableIDs(rawOffset,
count);
const StringEnumeration* tzs = TimeZone::createEnumeration(rawOffset);
if(tzs == 0) {
// TBD: U_MEMORY_ALLOCATION_ERROR
return 0;
}
uprv_free(tzs);
UErrorCode ec = U_ZERO_ERROR;
int32_t count = tzs->count(ec);
delete tzs;
return count;
}

View File

@ -35,6 +35,8 @@
U_NAMESPACE_BEGIN
class StringEnumeration;
/**
* <code>TimeZone</code> represents a time zone offset, and also figures out daylight
* savings.
@ -145,6 +147,46 @@ public:
*/
static TimeZone* createTimeZone(const UnicodeString& ID);
/**
* Returns an enumeration over all recognized time zone IDs, i.e.,
* all strings that createTimeZone() accepts.
*
* @return an enumeration object, owned by the caller.
* @draft ICU 2.4
*/
static StringEnumeration* createEnumeration();
/**
* Returns an enumeration over time zone IDs with a given raw
* offset from GMT. There may be several times zones with the
* same GMT offset that differ in the way they handle daylight
* savings time. For example, the state of Arizona doesn't
* observe daylight savings time. If you ask for the time zone
* IDs corresponding to GMT-7:00, you'll get back an enumeration
* over two time zone IDs: "America/Denver," which corresponds to
* Mountain Standard Time in the winter and Mountain Daylight Time
* in the summer, and "America/Phoenix", which corresponds to
* Mountain Standard Time year-round, even in the summer.
*
* @param rawOffset an offset from GMT in milliseconds, ignoring
* the effect of daylight savings time, if any
* @return an enumeration object, owned by the caller
* @draft ICU 2.4
*/
static StringEnumeration* createEnumeration(int32_t rawOffset);
/**
* Returns an enumeration over time zone IDs associated with the
* given country. Some zones are affiliated with no country
* (e.g., "UTC"); these may also be retrieved, as a group.
*
* @param country The ISO 3166 two-letter country code, or NULL to
* retrieve zones not affiliated with any country.
* @return an enumeration object, owned by the caller
* @draft ICU 2.4
*/
static StringEnumeration* createEnumeration(const char* country);
/**
* Returns a list of time zone IDs, one for each time zone with a given GMT offset.
* The return value is a list because there may be several times zones with the same
@ -156,7 +198,9 @@ public:
* Mountain Standard Time year-round, even in the summer.
* <P>
* The caller owns the list that is returned, but does not own the strings contained
* in that list. Delete the array with free() (not operator delete), but DON'T delete the elements in the array.
* in that list. Delete the array with uprv_free(), but DON'T delete the elements in the array.
*
* <p>NOTE: uprv_free() is declared in the private header source/cmemory.h.
*
* @param rawOffset An offset from GMT in milliseconds.
* @param numIDs Receives the number of items in the array that is returned.
@ -164,7 +208,7 @@ public:
* a time zone ID for a time zone with the given GMT offset. If
* there is no timezone that matches the GMT offset
* specified, NULL is returned.
* @stable
* @deprecated To be removed after 2003-Nov-8. Use createAvailableIDs(int32_t) instead.
*/
static const UnicodeString** createAvailableIDs(int32_t rawOffset, int32_t& numIDs);
@ -174,9 +218,11 @@ public:
* "UTC"); these may also be retrieved, as a group.
*
* <P>The caller owns the list that is returned, but does not own
* the strings contained in that list. Delete the array with free() (not operator delete), but
* the strings contained in that list. Delete the array with uprv_free(), but
* <b>DON'T</b> delete the elements in the array.
*
* <p>NOTE: uprv_free() is declared in the private header source/cmemory.h.
*
* @param country The ISO 3166 two-letter country code, or NULL to
* retrieve zones not affiliated with any country.
* @param numIDs Receives the number of items in the array that is
@ -185,6 +231,7 @@ public:
* UnicodeString is a time zone ID for a time zone with the given
* country. If there is no timezone that matches the country
* specified, NULL is returned.
* @deprecated To be removed after 2003-Nov-8. Use createAvailableIDs(const char*) instead.
*/
static const UnicodeString** createAvailableIDs(const char* country,
int32_t& numIDs);
@ -192,13 +239,15 @@ public:
/**
* Returns a list of all time zone IDs supported by the TimeZone class (i.e., all
* IDs that it's legal to pass to createTimeZone()). The caller owns the list that
* is returned, but does not own the strings contained in that list. Delete the array with free() (not operator delete),
* is returned, but does not own the strings contained in that list. Delete the array with uprv_free(),
* but DON'T delete the elements in the array.
*
* <p>NOTE: uprv_free() is declared in the private header source/cmemory.h.
*
* @param numIDs Receives the number of zone IDs returned.
* @return An array of UnicodeString pointers, where each is a time zone ID
* supported by the TimeZone class.
* @stable
* @deprecated To be removed after 2003-Nov-8. Use createAvailableIDs(void) instead.
*/
static const UnicodeString** createAvailableIDs(int32_t& numIDs);

View File

@ -7,6 +7,7 @@
#define UCAL_H
#include "unicode/utypes.h"
#include "unicode/uenum.h"
#if !UCONFIG_NO_FORMATTING
@ -279,6 +280,19 @@ enum UCalendarAMPMs {
/** @stable */
typedef enum UCalendarAMPMs UCalendarAMPMs;
/**
* Create a UEnumeration over the recognized time zone IDs with the
* given raw offset.
* @param rawOffset the desired GMT offset, not including the effects
* of daylight savings time
* @return an enumeration object that the caller must dispose of using
* uenum_close()
* @draft ICU 2.4
*/
U_CAPI UEnumeration* U_EXPORT2
ucal_openTimeZoneEnumeration(int32_t rawOffset,
UErrorCode* status);
/**
* Get an available TimeZone ID.
* A Timezone ID is a string of the form "America/Los Angeles".
@ -287,7 +301,7 @@ typedef enum UCalendarAMPMs UCalendarAMPMs;
* @param status A pointer to an UErrorCode to receive any errors
* @return The requested TimeZone ID, or 0 if not found
* @see ucal_countAvailableTZIDs
* @stable
* @deprecated To be removed after 2003-Nov-8. Use ucal_openTimeZoneEnumeration instead.
*/
U_CAPI const UChar* U_EXPORT2
ucal_getAvailableTZIDs( int32_t rawOffset,
@ -301,7 +315,7 @@ ucal_getAvailableTZIDs( int32_t rawOffset,
* @param rawOffset The desired GMT offset.
* @return The number of TimeZones with rawOffset.
* @see ucal_getAvailableTZIDs
* @stable
* @deprecated To be removed after 2003-Nov-8. Use ucal_openTimeZoneEnumeration instead.
*/
U_CAPI int32_t U_EXPORT2
ucal_countAvailableTZIDs(int32_t rawOffset);

View File

@ -48,6 +48,7 @@ static const UChar fgGMTID [] = { 0x0047, 0x004d, 0x0054, 0x0000 };
static void TestCalendar()
{
UCalendar *caldef = 0, *caldef2 = 0, *calfr = 0, *calit = 0;
UEnumeration* uenum = NULL;
int32_t count, count2, offset,i;
UChar *tzID = 0;
UChar *tzdname = 0;
@ -60,31 +61,64 @@ static void TestCalendar()
/*Testing countAvailableTimeZones*/
offset=0;
log_verbose("\nTesting countAvialableTimeZoneIds\n");
log_verbose("\nTesting ucal_countAvailableTZIDs\n");
count=ucal_countAvailableTZIDs(offset);
log_verbose("The number of timezone id's present with offset 0 are %d:\n", count);
if(count < 5) /* Don't hard code an exact == test here! */
log_err("FAIL: error in the countAvailableTZIDs - got %d expected at least 5 total\n", count);
log_err("FAIL: error in the ucal_countAvailableTZIDs - got %d expected at least 5 total\n", count);
/*Testing getAvialableTZIDs*/
log_verbose("\nTesting getAvailableTimezoneids");
/*Testing getAvailableTZIDs*/
log_verbose("\nTesting ucal_getAvailableTZIDs");
for(i=0;i<count;i++){
ucal_getAvailableTZIDs(offset, i, &status);
if(U_FAILURE(status)){
log_err("FAIL: There is an error in the getAvialableTZIDs the error is %s\n", myErrorName(status));
log_err("FAIL: ucal_getAvailableTZIDs returned %s\n", myErrorName(status));
}
log_verbose("%s\n", u_austrcpy(tempMsgBuf, ucal_getAvailableTZIDs(offset, i, &status)));
}
/*get Illegal TZID where index >= count*/
ucal_getAvailableTZIDs(offset, i, &status);
if(U_SUCCESS(status)){
log_err("FAIL: Expected U_INDEX_OUTOFBOUNDS_ERROR where index > count for TZID's");
}
if(status != U_INDEX_OUTOFBOUNDS_ERROR){
log_err("FAIL:for TZID index > count Expected INDEX_OUTOFBOUNDS_ERROR Got %s\n", myErrorName(status));
log_err("FAIL:for TZID index >= count Expected INDEX_OUTOFBOUNDS_ERROR Got %s\n", myErrorName(status));
}
status=U_ZERO_ERROR;
/*Test ucal_openTimeZoneEnumeration*/
offset=0;
uenum = ucal_openTimeZoneEnumeration(offset, &status);
if (U_FAILURE(status)) {
log_err("FAIL: ucal_openTimeZoneEnumeration failed with %s",
myErrorName(status));
} else {
const char* id;
int32_t len;
count = uenum_count(uenum, &status);
log_verbose("The number of timezone id's present with offset 0 is %d\n", count);
if (count < 5) { /* Don't hard code an exact == test here! */
log_err("FAIL: in ucal_openTimeZoneEnumeration, got %d, expected at least 5 for rawOffset 0\n", count);
}
uenum_reset(uenum, &status);
if (U_FAILURE(status)){
log_err("FAIL: uenum_reset for ucal_openTimeZoneEnumeration returned %s\n",
myErrorName(status));
}
for (i=0; i<count; i++) {
id = uenum_next(uenum, &len, &status);
if (U_FAILURE(status)){
log_err("FAIL: uenum_next for ucal_openTimeZoneEnumeration returned %s\n",
myErrorName(status));
} else {
log_verbose("%s\n", id);
}
}
/* Next one should be NULL */
id = uenum_next(uenum, &len, &status);
if (id != NULL) {
log_err("FAIL: uenum_next for ucal_openTimeZoneEnumeration returned %s, expected NULL\n",
id);
}
}
uenum_close(uenum);
/*Testing the ucal_open() function*/
log_verbose("\nTesting the ucal_open()\n");
@ -115,7 +149,7 @@ static void TestCalendar()
count=ucal_countAvailable();
/* use something sensible w/o hardcoding the count */
if(count > 0){
log_verbose("PASS: ucal_countAvialable() works fine\n");
log_verbose("PASS: ucal_countAvailable() works fine\n");
log_verbose("The no: of locales for which calendars are avilable are %d\n", count);
}
else

View File

@ -13,6 +13,7 @@
#include "unicode/gregocal.h"
#include "unicode/simpletz.h"
#include "unicode/smpdtfmt.h"
#include "unicode/strenum.h"
#include "cmemory.h"
#include <float.h>
@ -192,10 +193,10 @@ CalendarRegressionTest::test4031502()
// require the host zone to be set; it can be set in Java.
UErrorCode status = U_ZERO_ERROR;
int32_t count = 0;
const UnicodeString **ids = TimeZone::createAvailableIDs(count);
StringEnumeration* ids = TimeZone::createEnumeration();
UBool bad = FALSE;
for (int32_t i=0; i<count; ++i) {
TimeZone *zone = TimeZone::createTimeZone(*ids[i]);
for (int32_t i=0; i<ids->count(status); ++i) {
TimeZone *zone = TimeZone::createTimeZone(*ids->snext(status));
GregorianCalendar *cal = new GregorianCalendar(zone, status);
failure(status, "new GregorianCalendar");
cal->clear();
@ -214,7 +215,7 @@ CalendarRegressionTest::test4031502()
if (bad)
errln("TimeZone problems with GC");
// delete [] ids; // TODO: bad APIs
uprv_free(ids);
delete ids;
}
/**
@ -242,9 +243,10 @@ void CalendarRegressionTest::test4035301()
void CalendarRegressionTest::test4040996()
{
int32_t count = 0;
const UnicodeString **ids = TimeZone::createAvailableIDs(-8 * 60 * 60 * 1000, count);
SimpleTimeZone *pdt = new SimpleTimeZone(-8 * 60 * 60 * 1000, *ids[0]);
UErrorCode status = U_ZERO_ERROR;
StringEnumeration* ids = TimeZone::createEnumeration(-8 * 60 * 60 * 1000);
UErrorCode status = U_ZERO_ERROR;
count = ids->count(status);
SimpleTimeZone *pdt = new SimpleTimeZone(-8 * 60 * 60 * 1000, *ids->snext(status));
pdt->setStartRule(Calendar::APRIL, 1, Calendar::SUNDAY, 2 * 60 * 60 * 1000, status);
pdt->setEndRule(Calendar::OCTOBER, -1, Calendar::SUNDAY, 2 * 60 * 60 * 1000, status);
Calendar *calendar = new GregorianCalendar(pdt, status);
@ -274,7 +276,7 @@ void CalendarRegressionTest::test4040996()
errln(UnicodeString("Fail: Calendar::add misbehaves"));
delete calendar;
uprv_free(ids);
delete ids;
// delete ids; // TODO: BAD API
}

View File

@ -14,6 +14,7 @@
#include "unicode/smpdtfmt.h"
#include "unicode/datefmt.h"
#include "unicode/simpletz.h"
#include "unicode/strenum.h"
#include "cmemory.h"
// *****************************************************************************
@ -68,7 +69,8 @@ void DateFormatTest::TestWallyWedel()
* A String array for the time zone ids.
*/
int32_t ids_length;
const UnicodeString **ids = TimeZone::createAvailableIDs(ids_length);
StringEnumeration* ids = TimeZone::createEnumeration();
ids_length = ids->count(status);
/*
* How many ids do we have?
*/
@ -84,7 +86,8 @@ void DateFormatTest::TestWallyWedel()
Calendar *cal = Calendar::createInstance(status);
for (int32_t i = 0; i < ids_length; i++) {
// logln(i + " " + ids[i]);
TimeZone *ttz = TimeZone::createTimeZone(*ids[i]);
const UnicodeString* id = ids->snext(status);
TimeZone *ttz = TimeZone::createTimeZone(*id);
// offset = ttz.getRawOffset();
cal->setTimeZone(*ttz);
cal->setTime(today, status);
@ -123,13 +126,13 @@ void DateFormatTest::TestWallyWedel()
UBool ok = fmtDstOffset == 0 || *fmtDstOffset == dstOffset;
if (ok)
{
logln(UnicodeString() + i + " " + *ids[i] + " " + dstOffset +
logln(UnicodeString() + i + " " + *id + " " + dstOffset +
" " + fmtOffset +
(fmtDstOffset != 0 ? " ok" : " ?"));
}
else
{
errln(UnicodeString() + i + " " + *ids[i] + " " + dstOffset +
errln(UnicodeString() + i + " " + *id + " " + dstOffset +
" " + fmtOffset + " *** FAIL ***");
}
delete ttz;
@ -137,7 +140,7 @@ void DateFormatTest::TestWallyWedel()
}
delete cal;
// delete ids; // TODO: BAD API
uprv_free(ids);
delete ids;
delete sdf;
delete tz;
}

View File

@ -10,6 +10,7 @@
#include "unicode/simpletz.h"
#include "unicode/smpdtfmt.h"
#include "unicode/strenum.h"
#include "tzregts.h"
#include "calregts.h"
#include "cmemory.h"
@ -472,12 +473,14 @@ void TimeZoneRegressionTest:: Test4151406() {
(hh/2) + ':' +
((hh%2==0) ? "00" : "30");
//try {
UErrorCode ec = U_ZERO_ERROR;
int32_t count;
const UnicodeString **ids = TimeZone::createAvailableIDs(rawoffset, count);
StringEnumeration* ids = TimeZone::createEnumeration(rawoffset);
count = ids->count(ec);
if (count> max)
max = count;
logln(hname + ' ' + count +
((count > 0) ? (" e.g. " + *ids[0]) : UnicodeString("")));
((count > 0) ? (" e.g. " + *ids->snext(ec)) : UnicodeString("")));
// delete [] ids;
uprv_free(ids);
/*} catch (Exception e) {

View File

@ -13,6 +13,7 @@
#include "unicode/calendar.h"
#include "unicode/gregocal.h"
#include "unicode/resbund.h"
#include "unicode/strenum.h"
#include "tztest.h"
#include "cmemory.h"
@ -286,14 +287,16 @@ TimeZoneTest::TestVariousAPI518()
void
TimeZoneTest::TestGetAvailableIDs913()
{
UErrorCode ec = U_ZERO_ERROR;
UnicodeString str;
UnicodeString *buf = new UnicodeString("TimeZone.getAvailableIDs() = { ");
UnicodeString *buf = new UnicodeString("TimeZone::createEnumeration() = { ");
int32_t s_length;
const UnicodeString** s = TimeZone::createAvailableIDs(s_length);
StringEnumeration* s = TimeZone::createEnumeration();
s_length = s->count(ec);
int32_t i;
for (i = 0; i < s_length;++i) {
if (i > 0) *buf += ", ";
*buf += *s[i];
*buf += *s->snext(ec);
}
*buf += " };";
logln(*buf);
@ -302,31 +305,35 @@ TimeZoneTest::TestGetAvailableIDs913()
* zone, the last zone, and one in-between. This tests the binary
* search through the system zone data.
*/
for (i=0; i<3; ++i) {
int32_t which = (i==0)?0:((i==1)?(s_length/2):(s_length-1));
TimeZone *z = TimeZone::createTimeZone(*s[which]);
s->reset(ec);
int32_t middle = s_length/2;
for (i=0; i<s_length; ++i) {
const UnicodeString* id = s->snext(ec);
if (i==0 || i==middle || i==(s_length-1)) {
TimeZone *z = TimeZone::createTimeZone(*id);
if (z == 0) {
errln(UnicodeString("FAIL: createTimeZone(") +
*s[which] + ") -> 0");
} else if (z->getID(str) != *s[which]) {
*id + ") -> 0");
} else if (z->getID(str) != *id) {
errln(UnicodeString("FAIL: createTimeZone(") +
*s[which] + ") -> zone " + str);
*id + ") -> zone " + str);
} else {
logln(UnicodeString("OK: createTimeZone(") +
*s[which] + ") succeeded");
*id + ") succeeded");
}
delete z;
}
}
// delete [] s; ****BAD API ***
uprv_free(s);
delete s;
buf->truncate(0);
*buf += "TimeZone.getAvailableIDs(GMT+02:00) = { ";
*buf += "TimeZone::createEnumeration(GMT+02:00) = { ";
s = TimeZone::createAvailableIDs(+ 2 * 60 * 60 * 1000, s_length);
s = TimeZone::createEnumeration(+ 2 * 60 * 60 * 1000);
s_length = s->count(ec);
for (i = 0; i < s_length;++i) {
if (i > 0) *buf += ", ";
*buf += *s[i];
*buf += *s->snext(ec);
}
*buf += " };";
logln(*buf);
@ -349,8 +356,7 @@ TimeZoneTest::TestGetAvailableIDs913()
delete tz;
delete buf;
// delete [] s; // BAD API !!!!
uprv_free(s);
delete s;
}
@ -988,22 +994,25 @@ TimeZoneTest::TestAlternateRules()
void TimeZoneTest::TestCountries() {
// Make sure America/Los_Angeles is in the "US" group, and
// Asia/Tokyo isn't. Vice versa for the "JP" group.
UErrorCode ec = U_ZERO_ERROR;
int32_t n;
const UnicodeString** s = TimeZone::createAvailableIDs("US", n);
StringEnumeration* s = TimeZone::createEnumeration("US");
n = s->count(ec);
UBool la = FALSE, tokyo = FALSE;
UnicodeString laZone("America/Los_Angeles", "");
UnicodeString tokyoZone("Asia/Tokyo", "");
int32_t i;
if (s == NULL || n <= 0) {
errln("FAIL: TimeZone::createAvailableIDs() returned nothing");
errln("FAIL: TimeZone::createEnumeration() returned nothing");
return;
}
for (i=0; i<n; ++i) {
if (*s[i] == (laZone)) {
const UnicodeString* id = s->snext(ec);
if (*id == (laZone)) {
la = TRUE;
}
if (*s[i] == (tokyoZone)) {
if (*id == (tokyoZone)) {
tokyo = TRUE;
}
}
@ -1011,17 +1020,18 @@ void TimeZoneTest::TestCountries() {
errln("FAIL: " + laZone + " in US = " + la);
errln("FAIL: " + tokyoZone + " in US = " + tokyo);
}
// delete[] s; // TODO: BAD API
uprv_free(s);
delete s;
s = TimeZone::createAvailableIDs("JP", n);
s = TimeZone::createEnumeration("JP");
n = s->count(ec);
la = FALSE; tokyo = FALSE;
for (i=0; i<n; ++i) {
if (*s[i] == (laZone)) {
const UnicodeString* id = s->snext(ec);
if (*id == (laZone)) {
la = TRUE;
}
if (*s[i] == (tokyoZone)) {
if (*id == (tokyoZone)) {
tokyo = TRUE;
}
}
@ -1029,8 +1039,7 @@ void TimeZoneTest::TestCountries() {
errln("FAIL: " + laZone + " in JP = " + la);
errln("FAIL: " + tokyoZone + " in JP = " + tokyo);
}
// delete[] s; // TODO: bad API
uprv_free(s);
delete s;
}
#endif /* #if !UCONFIG_NO_FORMATTING */