mirror of
				https://github.com/RGBCube/serenity
				synced 2025-10-31 15:12:45 +00:00 
			
		
		
		
	LibUnicode: Generate unique time zone structures
Each of the 374 locales contain 156 time zone structures. Of these 58,344 structures, 13,578 are unique.
This commit is contained in:
		
							parent
							
								
									b14b37f386
								
							
						
					
					
						commit
						7af1818e76
					
				
					 1 changed files with 54 additions and 30 deletions
				
			
		|  | @ -55,6 +55,9 @@ constexpr auto s_calendar_symbols_list_index_type = "u8"sv; | ||||||
| using CalendarIndexType = u8; | using CalendarIndexType = u8; | ||||||
| constexpr auto s_calendar_index_type = "u8"sv; | constexpr auto s_calendar_index_type = "u8"sv; | ||||||
| 
 | 
 | ||||||
|  | using TimeZoneIndexType = u16; | ||||||
|  | constexpr auto s_time_zone_index_type = "u16"sv; | ||||||
|  | 
 | ||||||
| struct CalendarPattern : public Unicode::CalendarPattern { | struct CalendarPattern : public Unicode::CalendarPattern { | ||||||
|     bool contains_only_date_fields() const |     bool contains_only_date_fields() const | ||||||
|     { |     { | ||||||
|  | @ -367,11 +370,43 @@ struct AK::Traits<Calendar> : public GenericTraits<Calendar> { | ||||||
| }; | }; | ||||||
| 
 | 
 | ||||||
| struct TimeZone { | struct TimeZone { | ||||||
|  |     unsigned hash() const | ||||||
|  |     { | ||||||
|  |         auto hash = int_hash(time_zone); | ||||||
|  |         hash = pair_int_hash(hash, long_name); | ||||||
|  |         hash = pair_int_hash(hash, short_name); | ||||||
|  |         return hash; | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     bool operator==(TimeZone const& other) const | ||||||
|  |     { | ||||||
|  |         return (time_zone == other.time_zone) | ||||||
|  |             && (long_name == other.long_name) | ||||||
|  |             && (short_name == other.short_name); | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|     StringIndexType time_zone { 0 }; |     StringIndexType time_zone { 0 }; | ||||||
|     StringIndexType long_name { 0 }; |     StringIndexType long_name { 0 }; | ||||||
|     StringIndexType short_name { 0 }; |     StringIndexType short_name { 0 }; | ||||||
| }; | }; | ||||||
| 
 | 
 | ||||||
|  | template<> | ||||||
|  | struct AK::Formatter<TimeZone> : Formatter<FormatString> { | ||||||
|  |     ErrorOr<void> format(FormatBuilder& builder, TimeZone const& time_zone) | ||||||
|  |     { | ||||||
|  |         return Formatter<FormatString>::format(builder, | ||||||
|  |             "{{ {}, {}, {} }}", | ||||||
|  |             time_zone.time_zone, | ||||||
|  |             time_zone.long_name, | ||||||
|  |             time_zone.short_name); | ||||||
|  |     } | ||||||
|  | }; | ||||||
|  | 
 | ||||||
|  | template<> | ||||||
|  | struct AK::Traits<TimeZone> : public GenericTraits<TimeZone> { | ||||||
|  |     static unsigned hash(TimeZone const& t) { return t.hash(); } | ||||||
|  | }; | ||||||
|  | 
 | ||||||
| struct DayPeriod { | struct DayPeriod { | ||||||
|     Unicode::DayPeriod day_period {}; |     Unicode::DayPeriod day_period {}; | ||||||
|     u8 begin { 0 }; |     u8 begin { 0 }; | ||||||
|  | @ -380,7 +415,7 @@ struct DayPeriod { | ||||||
| 
 | 
 | ||||||
| struct Locale { | struct Locale { | ||||||
|     HashMap<String, CalendarIndexType> calendars; |     HashMap<String, CalendarIndexType> calendars; | ||||||
|     HashMap<String, TimeZone> time_zones; |     HashMap<String, TimeZoneIndexType> time_zones; | ||||||
|     Vector<DayPeriod> day_periods; |     Vector<DayPeriod> day_periods; | ||||||
| }; | }; | ||||||
| 
 | 
 | ||||||
|  | @ -395,6 +430,7 @@ struct UnicodeLocaleData { | ||||||
|     UniqueStorage<CalendarSymbols, CalendarSymbolsIndexType> unique_calendar_symbols; |     UniqueStorage<CalendarSymbols, CalendarSymbolsIndexType> unique_calendar_symbols; | ||||||
|     UniqueStorage<CalendarSymbolsList, CalendarSymbolsListIndexType> unique_calendar_symbols_lists; |     UniqueStorage<CalendarSymbolsList, CalendarSymbolsListIndexType> unique_calendar_symbols_lists; | ||||||
|     UniqueStorage<Calendar, CalendarIndexType> unique_calendars; |     UniqueStorage<Calendar, CalendarIndexType> unique_calendars; | ||||||
|  |     UniqueStorage<TimeZone, TimeZoneIndexType> unique_time_zones; | ||||||
| 
 | 
 | ||||||
|     HashMap<String, Locale> locales; |     HashMap<String, Locale> locales; | ||||||
| 
 | 
 | ||||||
|  | @ -1282,7 +1318,8 @@ static ErrorOr<void> parse_time_zone_names(String locale_time_zone_names_path, U | ||||||
|         if (!locale_data.time_zones.contains_slow(time_zone_name)) |         if (!locale_data.time_zones.contains_slow(time_zone_name)) | ||||||
|             locale_data.time_zones.append(time_zone_name); |             locale_data.time_zones.append(time_zone_name); | ||||||
| 
 | 
 | ||||||
|         locale.time_zones.set(time_zone_name, move(time_zone)); |         auto time_zone_index = locale_data.unique_time_zones.ensure(move(time_zone)); | ||||||
|  |         locale.time_zones.set(time_zone_name, time_zone_index); | ||||||
|     }; |     }; | ||||||
| 
 | 
 | ||||||
|     meta_zone_object.as_object().for_each_member([&](auto const& meta_zone, JsonValue const& value) { |     meta_zone_object.as_object().for_each_member([&](auto const& meta_zone, JsonValue const& value) { | ||||||
|  | @ -1465,6 +1502,7 @@ static void generate_unicode_locale_implementation(Core::File& file, UnicodeLoca | ||||||
|     generator.set("calendar_symbols_index_type"sv, s_calendar_symbols_index_type); |     generator.set("calendar_symbols_index_type"sv, s_calendar_symbols_index_type); | ||||||
|     generator.set("calendar_symbols_list_index_type"sv, s_calendar_symbols_list_index_type); |     generator.set("calendar_symbols_list_index_type"sv, s_calendar_symbols_list_index_type); | ||||||
|     generator.set("calendar_index_type"sv, s_calendar_index_type); |     generator.set("calendar_index_type"sv, s_calendar_index_type); | ||||||
|  |     generator.set("time_zone_index_type"sv, s_time_zone_index_type); | ||||||
| 
 | 
 | ||||||
|     generator.append(R"~~~( |     generator.append(R"~~~( | ||||||
| #include <AK/Array.h> | #include <AK/Array.h> | ||||||
|  | @ -1633,6 +1671,7 @@ struct DayPeriodData { | ||||||
|     locale_data.unique_calendar_symbols.generate(generator, "CalendarSymbols"sv, "s_calendar_symbols"sv, 10); |     locale_data.unique_calendar_symbols.generate(generator, "CalendarSymbols"sv, "s_calendar_symbols"sv, 10); | ||||||
|     locale_data.unique_calendar_symbols_lists.generate(generator, s_calendar_symbols_index_type, "s_calendar_symbol_lists"sv); |     locale_data.unique_calendar_symbols_lists.generate(generator, s_calendar_symbols_index_type, "s_calendar_symbol_lists"sv); | ||||||
|     locale_data.unique_calendars.generate(generator, "CalendarData"sv, "s_calendars"sv, 10); |     locale_data.unique_calendars.generate(generator, "CalendarData"sv, "s_calendars"sv, 10); | ||||||
|  |     locale_data.unique_time_zones.generate(generator, "TimeZoneData"sv, "s_time_zones"sv, 30); | ||||||
| 
 | 
 | ||||||
|     auto append_calendars = [&](String name, auto const& calendars) { |     auto append_calendars = [&](String name, auto const& calendars) { | ||||||
|         generator.set("name", name); |         generator.set("name", name); | ||||||
|  | @ -1658,35 +1697,18 @@ static constexpr Array<@calendar_index_type@, @size@> @name@ { {)~~~"); | ||||||
|         generator.set("size", String::number(locale_data.time_zones.size())); |         generator.set("size", String::number(locale_data.time_zones.size())); | ||||||
| 
 | 
 | ||||||
|         generator.append(R"~~~( |         generator.append(R"~~~( | ||||||
| static constexpr Array<TimeZoneData, @size@> @name@ { {)~~~"); | static constexpr Array<@time_zone_index_type@, @size@> @name@ { {)~~~"); | ||||||
| 
 |  | ||||||
|         constexpr size_t max_values_per_row = 20; |  | ||||||
|         size_t values_in_current_row = 0; |  | ||||||
| 
 | 
 | ||||||
|  |         bool first = true; | ||||||
|         for (auto const& time_zone_key : locale_data.time_zones) { |         for (auto const& time_zone_key : locale_data.time_zones) { | ||||||
|             auto time_zone = time_zones.find(time_zone_key); |             auto time_zone = time_zones.get(time_zone_key).value_or(0); | ||||||
| 
 | 
 | ||||||
|             if (values_in_current_row++ > 0) |             generator.append(first ? " " : ", "); | ||||||
|                 generator.append(" "); |             generator.append(String::number(time_zone)); | ||||||
| 
 |             first = false; | ||||||
|             if (time_zone == time_zones.end()) { |  | ||||||
|                 generator.append("{},"); |  | ||||||
|             } else { |  | ||||||
|                 generator.set("time_zone", String::number(time_zone->value.time_zone)); |  | ||||||
|                 generator.set("long_name", String::number(time_zone->value.long_name)); |  | ||||||
|                 generator.set("short_name", String::number(time_zone->value.short_name)); |  | ||||||
|                 generator.append("{ @time_zone@, @long_name@, @short_name@ },"); |  | ||||||
|         } |         } | ||||||
| 
 | 
 | ||||||
|             if (values_in_current_row == max_values_per_row) { |         generator.append(" } };"); | ||||||
|                 values_in_current_row = 0; |  | ||||||
|                 generator.append("\n    "); |  | ||||||
|             } |  | ||||||
|         } |  | ||||||
| 
 |  | ||||||
|         generator.append(R"~~~( |  | ||||||
| } }; |  | ||||||
| )~~~"); |  | ||||||
|     }; |     }; | ||||||
| 
 | 
 | ||||||
|     auto append_day_periods = [&](String name, auto const& day_periods) { |     auto append_day_periods = [&](String name, auto const& day_periods) { | ||||||
|  | @ -1724,7 +1746,7 @@ static constexpr Array<u8, @size@> @name@ { { )~~~"); | ||||||
|     }; |     }; | ||||||
| 
 | 
 | ||||||
|     generate_mapping(generator, locale_data.locales, s_calendar_index_type, "s_locale_calendars"sv, "s_calendars_{}", [&](auto const& name, auto const& value) { append_calendars(name, value.calendars); }); |     generate_mapping(generator, locale_data.locales, s_calendar_index_type, "s_locale_calendars"sv, "s_calendars_{}", [&](auto const& name, auto const& value) { append_calendars(name, value.calendars); }); | ||||||
|     generate_mapping(generator, locale_data.locales, "TimeZoneData"sv, "s_time_zones"sv, "s_time_zones_{}", [&](auto const& name, auto const& value) { append_time_zones(name, value.time_zones); }); |     generate_mapping(generator, locale_data.locales, s_time_zone_index_type, "s_locale_time_zones"sv, "s_time_zones_{}", [&](auto const& name, auto const& value) { append_time_zones(name, value.time_zones); }); | ||||||
|     generate_mapping(generator, locale_data.locales, "DayPeriodData"sv, "s_day_periods"sv, "s_day_periods_{}", [&](auto const& name, auto const& value) { append_day_periods(name, value.day_periods); }); |     generate_mapping(generator, locale_data.locales, "DayPeriodData"sv, "s_day_periods"sv, "s_day_periods_{}", [&](auto const& name, auto const& value) { append_day_periods(name, value.day_periods); }); | ||||||
|     generate_mapping(generator, locale_data.hour_cycle_regions, "u8"sv, "s_hour_cycles"sv, "s_hour_cycles_{}", [&](auto const& name, auto const& value) { append_hour_cycles(name, value); }); |     generate_mapping(generator, locale_data.hour_cycle_regions, "u8"sv, "s_hour_cycles"sv, "s_hour_cycles_{}", [&](auto const& name, auto const& value) { append_hour_cycles(name, value); }); | ||||||
| 
 | 
 | ||||||
|  | @ -1973,10 +1995,12 @@ static TimeZoneData const* find_time_zone_data(StringView locale, StringView tim | ||||||
|         return nullptr; |         return nullptr; | ||||||
| 
 | 
 | ||||||
|     auto locale_index = to_underlying(*locale_value) - 1; // Subtract 1 because 0 == Locale::None.
 |     auto locale_index = to_underlying(*locale_value) - 1; // Subtract 1 because 0 == Locale::None.
 | ||||||
|     auto time_zone_index = to_underlying(*time_zone_value); |     size_t time_zone_index = to_underlying(*time_zone_value); | ||||||
| 
 | 
 | ||||||
|     auto const& time_zones = s_time_zones.at(locale_index); |     auto const& time_zone_indices = s_locale_time_zones.at(locale_index); | ||||||
|     return &time_zones[time_zone_index]; |     time_zone_index = time_zone_indices.at(time_zone_index); | ||||||
|  | 
 | ||||||
|  |     return &s_time_zones[time_zone_index]; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| Optional<StringView> get_time_zone_name(StringView locale, StringView time_zone, CalendarPatternStyle style) | Optional<StringView> get_time_zone_name(StringView locale, StringView time_zone, CalendarPatternStyle style) | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Timothy Flynn
						Timothy Flynn