/** * @param int $nDays * @return static */ public static function fromInteger($nDays) { $fourCentury = 365 * 400 + static::nLeapYears(400); $century = 365 * 100 + static::nLeapYears(100); $fourYear = 365 * 4 + 1; $year = 1 + floor($nDays / $fourCentury) * 400; $nDays %= $fourCentury; $year += floor($nDays / $century) * 100; $nDays %= $century; $year += floor($nDays / $fourYear) * 4; $nDays %= $fourYear; $year += floor($nDays / 365); $nDays %= 365; if (static::isLeapYear($year) && $nDays >= 60) { if ($nDays == 60) { $month = 2; $day = 29; } else { $month = MiscHelpers::binarySearch($nDays, static::$cumulativeDaysInMonth); $day = $nDays - static::$cumulativeDaysInMonth[$month - 1] - 2; } } else { $month = MiscHelpers::binarySearch($nDays, static::$cumulativeDaysInMonth); $day = $nDays - static::$cumulativeDaysInMonth[$month - 1] - 1; } return new static($year, $month, $day); }
public function test_search() { $this->assertEquals(0, MiscHelpers::binarySearch(0, [0, 1])); $this->assertEquals(1, MiscHelpers::binarySearch(1, [0, 2])); $this->assertEquals(2, MiscHelpers::binarySearch(2, [0, 1])); $this->assertEquals(0, MiscHelpers::binarySearch(-1, [0, 1])); $this->assertEquals(1, MiscHelpers::binarySearch(1, [0, 1])); $this->assertEquals(0, MiscHelpers::binarySearch(0, [0, 1, 2, 3, 4, 5])); $this->assertEquals(1, MiscHelpers::binarySearch(1, [0, 2, 5, 6, 7])); $this->assertEquals(5, MiscHelpers::binarySearch(10, [0, 2, 5, 6, 7])); }
protected function numberOfLeapYearsPast() { $y = $this->getYear(); /** @var int $nHops number of 365-day-years followed a five-leap-year*/ $nHops = MiscHelpers::binarySearch($y + 1, static::$fiveLeapYears); return (int) (($y - $nHops) / 4); }