@@ -88,21 +88,21 @@ func FromStdTime(t time.Time) *Lunar {
8888
8989 offset := int (t .Truncate (time .Hour ).Sub (time .Date (minYear , 1 , 31 , 0 , 0 , 0 , 0 , t .Location ())).Hours () / 24 )
9090 for l .year = minYear ; l .year <= maxYear && offset > 0 ; l .year ++ {
91- daysInYear = l . getDaysInYear ()
91+ daysInYear = getDaysInYear (l . year )
9292 offset -= daysInYear
9393 }
9494 if offset < 0 {
9595 offset += daysInYear
9696 l .year --
9797 }
98- leapMonth = l . LeapMonth ( )
98+ leapMonth = getLeapMonth ( l . year )
9999 for l .month = 1 ; l .month <= 12 && offset > 0 ; l .month ++ {
100100 if leapMonth > 0 && l .month == (leapMonth + 1 ) && ! l .isLeapMonth {
101101 l .month --
102102 l .isLeapMonth = true
103- daysInMonth = l . getDaysInLeapMonth ()
103+ daysInMonth = getDaysInLeapMonth (l . year )
104104 } else {
105- daysInMonth = l . getDaysInMonth ()
105+ daysInMonth = getDaysInMonth (l . year , l . month )
106106 }
107107 offset -= daysInMonth
108108 if l .isLeapMonth && l .month == (leapMonth + 1 ) {
@@ -138,9 +138,9 @@ func (l *Lunar) ToGregorian(timezone ...string) *calendar.Gregorian {
138138 if g .Error != nil {
139139 return g
140140 }
141- days := l . getDaysInMonth ()
142- offset := l . getOffsetInYear ()
143- offset += l . getOffsetInMonth ()
141+ days := getDaysInMonth (l . year , l . month )
142+ offset := getOffsetInYear (l . year , l . month )
143+ offset += getOffsetInMonth (l . year )
144144
145145 // add the time difference of the month before the leap month
146146 if l .isLeapMonth {
@@ -197,7 +197,7 @@ func (l *Lunar) LeapMonth() int {
197197 if ! l .IsValid () {
198198 return 0
199199 }
200- return years [ l .year - minYear ] & 0xf
200+ return getLeapMonth ( l .year )
201201}
202202
203203// String implements "Stringer" interface for Lunar.
@@ -431,56 +431,80 @@ func (l *Lunar) IsPigYear() bool {
431431 return false
432432}
433433
434- func (l * Lunar ) getOffsetInYear () int {
434+ // getOffsetInYear calculates the total number of days from the beginning of the year to the specified month.
435+ // It handles leap months by adding the leap month days when encountered.
436+ // Returns the offset in days.
437+ func getOffsetInYear (year , month int ) int {
435438 flag := false
436- clone , month , offset := * l , 0 , 0
437- for month = 1 ; month < l . month ; month ++ {
438- leapMonth := l . LeapMonth ( )
439+ offset := 0
440+ for m : = 1 ; m < month ; m ++ {
441+ leapMonth := getLeapMonth ( year )
439442 if ! flag {
440- // 处理闰月
441- if leapMonth <= month && leapMonth > 0 {
442- offset += l .getDaysInLeapMonth ()
443+ if leapMonth <= m && leapMonth > 0 {
444+ offset += getDaysInLeapMonth (year )
443445 flag = true
444446 }
445447 }
446- clone .month = month
447- offset += clone .getDaysInMonth ()
448+ offset += getDaysInMonth (year , m )
448449 }
449450 return offset
450451}
451452
452- func (l * Lunar ) getOffsetInMonth () int {
453- clone , year , offset := * l , 0 , 0
454- for year = minYear ; year < l .year ; year ++ {
455- clone .year = year
456- offset += clone .getDaysInYear ()
453+ // getOffsetInMonth calculates the total number of days from the minimum year (1900) to the specified year.
454+ // This represents the cumulative days across all years up to but not including the target year.
455+ // Returns the offset in days.
456+ func getOffsetInMonth (year int ) int {
457+ offset := 0
458+ for y := minYear ; y < year ; y ++ {
459+ offset += getDaysInYear (y )
457460 }
458461 return offset
459462}
460463
461- func (l * Lunar ) getDaysInYear () int {
464+ // getDaysInYear calculates the total number of days in a lunar year.
465+ // It uses the lunar calendar data array to determine which months have 30 days vs 29 days.
466+ // The base is 348 days (12 months × 29 days), then adds days for months with 30 days.
467+ // Finally adds the leap month days if the year has a leap month.
468+ // Returns the total number of days in the year.
469+ func getDaysInYear (year int ) int {
462470 var days = 348
463471 for i := 0x8000 ; i > 0x8 ; i >>= 1 {
464- if (years [l . year - minYear ] & i ) != 0 {
472+ if (years [year - minYear ] & i ) != 0 {
465473 days ++
466474 }
467475 }
468- return days + l . getDaysInLeapMonth ()
476+ return days + getDaysInLeapMonth (year )
469477}
470478
471- func (l * Lunar ) getDaysInMonth () int {
472- if (years [l .year - minYear ] & (0x10000 >> uint (l .month ))) != 0 {
479+ // getDaysInMonth calculates the number of days in a specific lunar month.
480+ // It uses the lunar calendar data array to determine if the month has 30 or 29 days.
481+ // The bit pattern in the data array indicates which months are long (30 days).
482+ // Returns 30 for long months, 29 for short months.
483+ func getDaysInMonth (year , month int ) int {
484+ if (years [year - minYear ] & (0x10000 >> uint (month ))) != 0 {
473485 return 30
474486 }
475487 return 29
476488}
477489
478- func (l * Lunar ) getDaysInLeapMonth () int {
479- if l .LeapMonth () == 0 {
490+ // getDaysInLeapMonth calculates the number of days in the leap month of a lunar year.
491+ // If the year has no leap month, returns 0.
492+ // If the year has a leap month, determines if it's a long (30 days) or short (29 days) month.
493+ // Returns the number of days in the leap month, or 0 if no leap month exists.
494+ func getDaysInLeapMonth (year int ) int {
495+ if getLeapMonth (year ) == 0 {
480496 return 0
481497 }
482- if years [l . year - minYear ]& 0x10000 != 0 {
498+ if years [year - minYear ]& 0x10000 != 0 {
483499 return 30
484500 }
485501 return 29
486502}
503+
504+ // getLeapMonth determines which month is the leap month in a lunar year.
505+ // Returns 0 if the year has no leap month, or the month number (1-12) if a leap month exists.
506+ // The leap month information is stored in the lower 4 bits of the lunar calendar data.
507+ // Returns 0 for years outside the supported range (1900-2100).
508+ func getLeapMonth (year int ) int {
509+ return years [year - minYear ] & 0xf
510+ }
0 commit comments