@@ -220,44 +220,9 @@ impl HijriTabular {
220
220
}
221
221
}
222
222
223
- /// Compact representation of the length of a Hijri year.
224
- #[ derive( Copy , Clone , Debug , Hash , PartialEq , Eq , PartialOrd , Ord ) ]
225
- enum HijriYearLength {
226
- /// Long (355-day) Hijri year
227
- L355 ,
228
- /// Short (354-day) Hijri year
229
- L354 ,
230
- /// Unexpectedly Short (353-day) Hijri year
231
- ///
232
- /// It is probably a bug when this year length is returned. See:
233
- /// <https://github.com/unicode-org/icu4x/issues/4930>
234
- L353 ,
235
- }
236
-
237
- impl Default for HijriYearLength {
238
- fn default ( ) -> Self {
239
- Self :: L354
240
- }
241
- }
242
-
243
- impl HijriYearLength {
244
- const LONG : u16 = 355 ;
245
- const SHORT : u16 = 354 ;
246
-
247
- fn try_from_int ( value : i64 ) -> Option < Self > {
248
- match value {
249
- 355 => Some ( Self :: L355 ) ,
250
- 354 => Some ( Self :: L354 ) ,
251
- 353 => Some ( Self :: L353 ) ,
252
- _ => None ,
253
- }
254
- }
255
- }
256
-
257
223
#[ derive( Copy , Clone , Debug , Hash , PartialEq , Eq , PartialOrd , Ord ) ]
258
224
pub ( crate ) struct HijriYearInfo < IB : IslamicBased > {
259
- packed_data : PackedHijriYearInfo ,
260
- prev_year_length : HijriYearLength ,
225
+ pub ( crate ) packed_data : PackedHijriYearInfo ,
261
226
model : IB ,
262
227
value : i32 ,
263
228
}
@@ -268,56 +233,58 @@ impl<IB: IslamicBased> From<HijriYearInfo<IB>> for i32 {
268
233
}
269
234
}
270
235
236
+ const LONG_YEAR_LEN : u16 = 355 ;
237
+ const SHORT_YEAR_LEN : u16 = 354 ;
238
+
271
239
impl < IB : IslamicBased > HijriYearInfo < IB > {
272
- pub ( crate ) fn new (
273
- prev_packed : PackedHijriYearInfo ,
274
- this_packed : PackedHijriYearInfo ,
240
+ pub ( crate ) fn from_packed (
241
+ packed_data : PackedHijriYearInfo ,
275
242
extended_year : i32 ,
276
243
model : IB ,
277
244
) -> Self {
278
- let days_in_year = prev_packed. days_in_year ( ) ;
279
- let days_in_year = match HijriYearLength :: try_from_int ( days_in_year as i64 ) {
280
- Some ( x) => x,
281
- None => {
282
- debug_assert ! ( false , "Found wrong year length for Hijri year {extended_year}: Expected 355, 354, or 353, got {days_in_year}" ) ;
283
- Default :: default ( )
284
- }
285
- } ;
286
245
Self {
287
- prev_year_length : days_in_year,
288
- packed_data : this_packed,
246
+ packed_data,
289
247
model,
290
248
value : extended_year,
291
249
}
292
250
}
293
251
294
- fn compute_for_year ( extended_year : i32 , model : IB ) -> Self {
252
+ pub ( crate ) fn compute_for_year ( extended_year : i32 , model : IB ) -> Self {
295
253
let ny = model. fixed_from_islamic ( extended_year, 1 , 1 ) ;
296
- let packed_data = PackedHijriYearInfo :: compute_with_ny ( extended_year, ny, model) ;
297
- let prev_ny = model. fixed_from_islamic ( extended_year - 1 , 1 , 1 ) ;
298
- let rd_diff = ny - prev_ny;
299
- let rd_diff = match HijriYearLength :: try_from_int ( rd_diff) {
300
- Some ( x) => x,
301
- None => {
302
- debug_assert ! ( false , "({}) Found wrong year length for Hijri year {extended_year}: Expected 355, 354, or 353, got {rd_diff}" , IB :: DEBUG_NAME ) ;
303
- Default :: default ( )
304
- }
305
- } ;
306
- Self {
307
- prev_year_length : rd_diff,
308
- packed_data,
254
+ let month_lengths = model. month_lengths_for_year ( extended_year, ny) ;
255
+ let ny_offset = ny - IB :: mean_synodic_ny ( extended_year) ;
256
+ let r = Self {
257
+ packed_data : PackedHijriYearInfo :: new ( month_lengths, ny_offset) ,
309
258
model,
310
259
value : extended_year,
260
+ } ;
261
+ if !matches ! ( r. days_in_year( ) , SHORT_YEAR_LEN | LONG_YEAR_LEN | 353 ) {
262
+ // See https://github.com/unicode-org/icu4x/issues/4930
263
+ debug_assert ! ( false , "({}) Found wrong year length for Hijri year {extended_year}: Expected 355, 354, or 353, got {}" , IB :: DEBUG_NAME , r. days_in_year( ) ) ;
311
264
}
265
+ r
312
266
}
313
267
314
268
fn compute_for_fixed ( fixed : RataDie , model : IB ) -> Self {
315
269
let ( y, _m, _d) = model. islamic_from_fixed ( fixed) ;
316
270
Self :: compute_for_year ( y, model)
317
271
}
318
272
273
+ /// The number of days in a given 1-indexed month
274
+ pub ( crate ) fn days_in_month ( self , month : u8 ) -> u8 {
275
+ if self . packed_data . month_has_30_days ( month) {
276
+ 30
277
+ } else {
278
+ 29
279
+ }
280
+ }
281
+
282
+ pub ( crate ) fn days_in_year ( self ) -> u16 {
283
+ self . packed_data . last_day_of_month ( 12 )
284
+ }
285
+
319
286
/// Get the new year R.D. given the extended year that this yearinfo is for
320
- fn new_year ( self ) -> RataDie {
287
+ pub ( crate ) fn new_year ( self ) -> RataDie {
321
288
IB :: mean_synodic_ny ( self . value ) + self . packed_data . ny_offset ( )
322
289
}
323
290
@@ -401,20 +368,20 @@ impl CalendarArithmetic for HijriObservational {
401
368
type YearInfo = HijriYearInfo < ObservationalIslamic > ;
402
369
403
370
fn days_in_provided_month ( year : Self :: YearInfo , month : u8 ) -> u8 {
404
- year. packed_data . days_in_month ( month)
371
+ year. days_in_month ( month)
405
372
}
406
373
407
374
fn months_in_provided_year ( _year : Self :: YearInfo ) -> u8 {
408
375
12
409
376
}
410
377
411
378
fn days_in_provided_year ( year : Self :: YearInfo ) -> u16 {
412
- year. packed_data . days_in_year ( )
379
+ year. days_in_year ( )
413
380
}
414
381
415
382
// As an true lunar calendar, it does not have leap years.
416
383
fn provided_year_is_leap ( year : Self :: YearInfo ) -> bool {
417
- year. packed_data . days_in_year ( ) != HijriYearLength :: SHORT
384
+ year. days_in_year ( ) != SHORT_YEAR_LEN
418
385
}
419
386
420
387
fn last_month_day_in_provided_year ( year : Self :: YearInfo ) -> ( u8 , u8 ) {
@@ -574,20 +541,20 @@ impl CalendarArithmetic for HijriUmmAlQura {
574
541
type YearInfo = HijriYearInfo < SaudiIslamic > ;
575
542
576
543
fn days_in_provided_month ( year : Self :: YearInfo , month : u8 ) -> u8 {
577
- year. packed_data . days_in_month ( month)
544
+ year. days_in_month ( month)
578
545
}
579
546
580
547
fn months_in_provided_year ( _year : HijriYearInfo < SaudiIslamic > ) -> u8 {
581
548
12
582
549
}
583
550
584
551
fn days_in_provided_year ( year : Self :: YearInfo ) -> u16 {
585
- year. packed_data . days_in_year ( )
552
+ year. days_in_year ( )
586
553
}
587
554
588
555
// As an true lunar calendar, it does not have leap years.
589
556
fn provided_year_is_leap ( year : Self :: YearInfo ) -> bool {
590
- year. packed_data . days_in_year ( ) != HijriYearLength :: SHORT
557
+ year. days_in_year ( ) != SHORT_YEAR_LEN
591
558
}
592
559
593
560
fn last_month_day_in_provided_year ( year : HijriYearInfo < SaudiIslamic > ) -> ( u8 , u8 ) {
@@ -759,9 +726,9 @@ impl CalendarArithmetic for HijriCivil {
759
726
760
727
fn days_in_provided_year ( year : i32 ) -> u16 {
761
728
if Self :: provided_year_is_leap ( year) {
762
- HijriYearLength :: LONG
729
+ LONG_YEAR_LEN
763
730
} else {
764
- HijriYearLength :: SHORT
731
+ SHORT_YEAR_LEN
765
732
}
766
733
}
767
734
@@ -937,9 +904,9 @@ impl CalendarArithmetic for HijriTabular {
937
904
938
905
fn days_in_provided_year ( year : i32 ) -> u16 {
939
906
if Self :: provided_year_is_leap ( year) {
940
- HijriYearLength :: LONG
907
+ LONG_YEAR_LEN
941
908
} else {
942
- HijriYearLength :: SHORT
909
+ SHORT_YEAR_LEN
943
910
}
944
911
}
945
912
0 commit comments