From 390d736f891b0a5d14d815b9130e51693a346628 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felipe=20Balbont=C3=ADn?= Date: Mon, 12 Sep 2016 21:01:16 +0000 Subject: [PATCH] ICU-12591 Removed the CalendarData class and refactored all the remaining functions that used it (ICU4C). X-SVN-Rev: 39190 --- icu4c/source/i18n/calendar.cpp | 31 +++++++++++--- icu4c/source/i18n/dtitvfmt.cpp | 27 ++++++------ icu4c/source/i18n/dtptngen.cpp | 27 +++++++++--- icu4c/source/i18n/gregoimp.cpp | 78 ---------------------------------- icu4c/source/i18n/gregoimp.h | 37 ---------------- 5 files changed, 58 insertions(+), 142 deletions(-) diff --git a/icu4c/source/i18n/calendar.cpp b/icu4c/source/i18n/calendar.cpp index 53de270eaa7..ffa1e1da0be 100644 --- a/icu4c/source/i18n/calendar.cpp +++ b/icu4c/source/i18n/calendar.cpp @@ -636,7 +636,9 @@ static const int32_t kCalendarLimits[UCAL_FIELD_COUNT][4] = { }; // Resource bundle tags read by this class +static const char gCalendar[] = "calendar"; static const char gMonthNames[] = "monthNames"; +static const char gGregorian[] = "gregorian"; // Data flow in Calendar // --------------------- @@ -3793,12 +3795,30 @@ Calendar::setWeekData(const Locale& desiredLocale, const char *type, UErrorCode& from the calendar data. The code used to use the dateTimeElements resource to get first day of week data, but this was moved to supplemental data under ticket 7755. (JCE) */ - CalendarData calData(useLocale,type,status); - UResourceBundle *monthNames = calData.getByKey(gMonthNames,status); + // Get the monthNames resource bundle for the calendar 'type'. Fallback to gregorian if the resource is not + // found. + LocalUResourceBundlePointer calData(ures_open(NULL, useLocale.getBaseName(), &status)); + ures_getByKey(calData.getAlias(), gCalendar, calData.getAlias(), &status); + + LocalUResourceBundlePointer monthNames; + if (type != NULL && *type != '\0' && uprv_strcmp(type, gGregorian) != 0) { + monthNames.adoptInstead(ures_getByKeyWithFallback(calData.getAlias(), type, NULL, &status)); + ures_getByKeyWithFallback(monthNames.getAlias(), gMonthNames, + monthNames.getAlias(), &status); + } + + if (monthNames.isNull() || status == U_MISSING_RESOURCE_ERROR) { + status = U_ZERO_ERROR; + monthNames.adoptInstead(ures_getByKeyWithFallback(calData.getAlias(), gGregorian, + monthNames.orphan(), &status)); + ures_getByKeyWithFallback(monthNames.getAlias(), gMonthNames, + monthNames.getAlias(), &status); + } + if (U_SUCCESS(status)) { U_LOCALE_BASED(locBased,*this); - locBased.setLocaleIDs(ures_getLocaleByType(monthNames, ULOC_VALID_LOCALE, &status), - ures_getLocaleByType(monthNames, ULOC_ACTUAL_LOCALE, &status)); + locBased.setLocaleIDs(ures_getLocaleByType(monthNames.getAlias(), ULOC_VALID_LOCALE, &status), + ures_getLocaleByType(monthNames.getAlias(), ULOC_ACTUAL_LOCALE, &status)); } else { status = U_USING_FALLBACK_WARNING; return; @@ -3817,9 +3837,6 @@ Calendar::setWeekData(const Locale& desiredLocale, const char *type, UErrorCode& } if (U_FAILURE(status)) { -#if defined (U_DEBUG_CALDATA) - fprintf(stderr, " Failure loading weekData from supplemental = %s\n", u_errorName(status)); -#endif status = U_USING_FALLBACK_WARNING; } else { int32_t arrLen; diff --git a/icu4c/source/i18n/dtitvfmt.cpp b/icu4c/source/i18n/dtitvfmt.cpp index fe1947f1379..15c80e6d926 100644 --- a/icu4c/source/i18n/dtitvfmt.cpp +++ b/icu4c/source/i18n/dtitvfmt.cpp @@ -26,8 +26,8 @@ #include "cmemory.h" #include "cstring.h" #include "dtitv_impl.h" -#include "gregoimp.h" #include "mutex.h" +#include "uresimp.h" #ifdef DTITVFMT_DEBUG #include @@ -53,7 +53,9 @@ static const UChar gDateFormatSkeleton[][11] = { {LOW_Y, CAP_M, LOW_D, 0} }; -static const char gDateTimePatternsTag[]="DateTimePatterns"; +static const char gCalendarTag[] = "calendar"; +static const char gGregorianTag[] = "gregorian"; +static const char gDateTimePatternsTag[] = "DateTimePatterns"; // latestFirst: @@ -653,27 +655,22 @@ DateIntervalFormat::initializePattern(UErrorCode& status) { // with the time interval. // The date/time pattern ( such as {0} {1} ) is saved in // calendar, that is why need to get the CalendarData here. - CalendarData* calData = new CalendarData(locale, NULL, status); - if ( U_FAILURE(status) ) { - delete calData; - return; - } - if ( calData == NULL ) { - status = U_MEMORY_ALLOCATION_ERROR; - return; - } + LocalUResourceBundlePointer dateTimePatternsRes(ures_open(NULL, locale.getBaseName(), &status)); + ures_getByKey(dateTimePatternsRes.getAlias(), gCalendarTag, + dateTimePatternsRes.getAlias(), &status); + ures_getByKeyWithFallback(dateTimePatternsRes.getAlias(), gGregorianTag, + dateTimePatternsRes.getAlias(), &status); + ures_getByKeyWithFallback(dateTimePatternsRes.getAlias(), gDateTimePatternsTag, + dateTimePatternsRes.getAlias(), &status); - const UResourceBundle* dateTimePatternsRes = calData->getByKey( - gDateTimePatternsTag, status); int32_t dateTimeFormatLength; const UChar* dateTimeFormat = ures_getStringByIndex( - dateTimePatternsRes, + dateTimePatternsRes.getAlias(), (int32_t)DateFormat::kDateTime, &dateTimeFormatLength, &status); if ( U_SUCCESS(status) && dateTimeFormatLength >= 3 ) { fDateTimeFormat = new UnicodeString(dateTimeFormat, dateTimeFormatLength); } - delete calData; } UBool found = setSeparateDateTimePtn(normalizedDateSkeleton, diff --git a/icu4c/source/i18n/dtptngen.cpp b/icu4c/source/i18n/dtptngen.cpp index 6285b4341eb..c5fead15f1e 100644 --- a/icu4c/source/i18n/dtptngen.cpp +++ b/icu4c/source/i18n/dtptngen.cpp @@ -33,7 +33,6 @@ #include "cmemory.h" #include "cstring.h" #include "locbased.h" -#include "gregoimp.h" #include "hash.h" #include "uhash.h" #include "uresimp.h" @@ -1094,16 +1093,34 @@ DateTimePatternGenerator::setDateTimeFromCalendar(const Locale& locale, UErrorCo Calendar* fCalendar = Calendar::createInstance(locale, status); if (U_FAILURE(status)) { return; } - CalendarData calData(locale, fCalendar?fCalendar->getType():NULL, status); - UResourceBundle *dateTimePatterns = calData.getByKey(DT_DateTimePatternsTag, status); + + LocalUResourceBundlePointer calData(ures_open(NULL, locale.getBaseName(), &status)); + ures_getByKey(calData.getAlias(), DT_DateTimeCalendarTag, calData.getAlias(), &status); + + LocalUResourceBundlePointer dateTimePatterns; + if (fCalendar != NULL && fCalendar->getType() != NULL && *fCalendar->getType() != '\0' + && uprv_strcmp(fCalendar->getType(), DT_DateTimeGregorianTag) != 0) { + dateTimePatterns.adoptInstead(ures_getByKeyWithFallback(calData.getAlias(), fCalendar->getType(), + NULL, &status)); + ures_getByKeyWithFallback(dateTimePatterns.getAlias(), DT_DateTimePatternsTag, + dateTimePatterns.getAlias(), &status); + } + + if (dateTimePatterns.isNull() || status == U_MISSING_RESOURCE_ERROR) { + status = U_ZERO_ERROR; + dateTimePatterns.adoptInstead(ures_getByKeyWithFallback(calData.getAlias(), DT_DateTimeGregorianTag, + dateTimePatterns.orphan(), &status)); + ures_getByKeyWithFallback(dateTimePatterns.getAlias(), DT_DateTimePatternsTag, + dateTimePatterns.getAlias(), &status); + } if (U_FAILURE(status)) { return; } - if (ures_getSize(dateTimePatterns) <= DateFormat::kDateTime) + if (ures_getSize(dateTimePatterns.getAlias()) <= DateFormat::kDateTime) { status = U_INVALID_FORMAT_ERROR; return; } - resStr = ures_getStringByIndex(dateTimePatterns, (int32_t)DateFormat::kDateTime, &resStrLen, &status); + resStr = ures_getStringByIndex(dateTimePatterns.getAlias(), (int32_t)DateFormat::kDateTime, &resStrLen, &status); setDateTimeFormat(UnicodeString(TRUE, resStr, resStrLen)); delete fCalendar; diff --git a/icu4c/source/i18n/gregoimp.cpp b/icu4c/source/i18n/gregoimp.cpp index 8f634216310..1b313602d61 100644 --- a/icu4c/source/i18n/gregoimp.cpp +++ b/icu4c/source/i18n/gregoimp.cpp @@ -20,10 +20,6 @@ #include "cstring.h" #include "uassert.h" -#if defined(U_DEBUG_CALDATA) -#include -#endif - U_NAMESPACE_BEGIN int32_t ClockMath::floorDivide(int32_t numerator, int32_t denominator) { @@ -159,80 +155,6 @@ int32_t Grego::dayOfWeekInMonth(int32_t year, int32_t month, int32_t dom) { return weekInMonth; } -/* ---- CalendarData ------ */ - -#define U_CALENDAR_KEY "calendar" -#define U_GREGORIAN_KEY "gregorian" -#define U_FORMAT_KEY "format" -#define U_DEFAULT_KEY "default" -#define U_CALENDAR_DATA ((char*)0) - - -// CalendarData::CalendarData(const Locale& loc, UErrorCode& status) -// : fFillin(NULL), fBundle(NULL), fFallback(NULL) { -// initData(loc.getBaseName(), (char*) "???", status); -// } - -CalendarData::CalendarData(const Locale& loc, const char *type, UErrorCode& status) - : fFillin(NULL), fOtherFillin(NULL), fBundle(NULL), fFallback(NULL) { - initData(loc.getBaseName(), type, status); -} - -void CalendarData::initData(const char *locale, const char *type, UErrorCode& status) { - fOtherFillin = ures_open(U_CALENDAR_DATA, locale, &status); - fFillin = ures_getByKey(fOtherFillin, U_CALENDAR_KEY, fFillin, &status); - - if((type != NULL) && - (*type != '\0') && - (uprv_strcmp(type, U_GREGORIAN_KEY))) - { - fBundle = ures_getByKeyWithFallback(fFillin, type, NULL, &status); - fFallback = ures_getByKeyWithFallback(fFillin, U_GREGORIAN_KEY, NULL, &status); - -#if defined (U_DEBUG_CALDATA) - fprintf(stderr, "%p: CalendarData(%s, %s, %s) -> main(%p, %s)=%s, fallback(%p, %s)=%s\n", - this, locale, type, u_errorName(status), fBundle, type, fBundle?ures_getLocale(fBundle, &status):"", - fFallback, U_GREGORIAN_KEY, fFallback?ures_getLocale(fFallback, &status):""); -#endif - - } else { - fBundle = ures_getByKeyWithFallback(fFillin, U_GREGORIAN_KEY, NULL, &status); -#if defined (U_DEBUG_CALDATA) - fprintf(stderr, "%p: CalendarData(%s, %s, %s) -> main(%p, %s)=%s, fallback = NULL\n", - this, locale, type, u_errorName(status), fBundle, U_GREGORIAN_KEY, fBundle?ures_getLocale(fBundle, &status):"" ); -#endif - } -} - -CalendarData::~CalendarData() { - ures_close(fFillin); - ures_close(fBundle); - ures_close(fFallback); - ures_close(fOtherFillin); -} - -UResourceBundle* -CalendarData::getByKey(const char *key, UErrorCode& status) { - if(U_FAILURE(status)) { - return NULL; - } - - if(fBundle) { - fFillin = ures_getByKeyWithFallback(fBundle, key, fFillin, &status); -#if defined (U_DEBUG_CALDATA) - fprintf(stderr, "%p: get %s -> %s - from MAIN %s\n",this, key, u_errorName(status), ures_getLocale(fFillin, &status)); -#endif - } - if(fFallback && (status == U_MISSING_RESOURCE_ERROR)) { - status = U_ZERO_ERROR; // retry with fallback (gregorian) - fFillin = ures_getByKeyWithFallback(fFallback, key, fFillin, &status); -#if defined (U_DEBUG_CALDATA) - fprintf(stderr, "%p: get %s -> %s - from FALLBACK %s\n",this, key, u_errorName(status), ures_getLocale(fFillin, &status)); -#endif - } - return fFillin; -} - U_NAMESPACE_END #endif diff --git a/icu4c/source/i18n/gregoimp.h b/icu4c/source/i18n/gregoimp.h index 21ab83c285c..27303a6ac52 100644 --- a/icu4c/source/i18n/gregoimp.h +++ b/icu4c/source/i18n/gregoimp.h @@ -293,43 +293,6 @@ inline int32_t Grego::gregorianShift(int32_t eyear) { return gregShift; } -/** - * This utility class provides convenient access to the data needed for a calendar. - * @internal ICU 3.0 - */ -class CalendarData : public UMemory { -public: - /** - * Construct a CalendarData from the given locale. - * @param loc locale to use. The 'calendar' keyword will be ignored. - * @param type calendar type. NULL indicates the gregorian calendar. - * No default lookup is done. - * @param status error code - */ - CalendarData(const Locale& loc, const char *type, UErrorCode& status); - - /** - * Load data for calendar. Note, this object owns the resources, do NOT call ures_close()! - * The ResourceBundle C++ API should NOT be used because it is too slow for a low level API. - * - * @param key Resource key to data - * @param status Error Status - * @internal - */ - UResourceBundle* getByKey(const char *key, UErrorCode& status); - - ~CalendarData(); - -private: - void initData(const char *locale, const char *type, UErrorCode& status); - - UResourceBundle *fFillin; - UResourceBundle *fOtherFillin; - UResourceBundle *fBundle; - UResourceBundle *fFallback; - CalendarData(); // Not implemented. -}; - U_NAMESPACE_END #endif // !UCONFIG_NO_FORMATTING