Created
January 9, 2014 22:00
-
-
Save mikemix/8342861 to your computer and use it in GitHub Desktop.
Job interview task solved: day of week calculation
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
interface ImaginaryCalendarFinderInterface | |
{ | |
/** | |
* @param int $year | |
* @param int $month | |
* @param int $day | |
* @return int | |
*/ | |
public function dayOfTheWeek($year, $month, $day); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
interface ImaginaryCalendarInterface | |
{ | |
/** | |
* Get the name of the $day. | |
* | |
* @return string | |
*/ | |
public function getDayName($day); | |
/** | |
* Get days of the week array. | |
* | |
* @return array | |
*/ | |
public function getDaysOfTheWeek(); | |
/** | |
* Return is $year a leap year. | |
* | |
* @param int $year | |
* @return bool | |
*/ | |
public function isLeapYear($year); | |
/** | |
* Return number of days in the given $month. | |
* | |
* @param int $month | |
* @param int $days | |
* @return int Days in given $month due to leap year | |
*/ | |
public function getDaysInMonthOfLeapYear($month, $days); | |
/** | |
* Return months and number of days for each month as an array. | |
* Example output: | |
* [1] => 30, [2] => 27, [3] => 31, ... | |
* | |
* @return array | |
*/ | |
public function getMonthsAndDaysCount(); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
function __autoload($name) | |
{ | |
require __DIR__ . DIRECTORY_SEPARATOR . $name . '.php'; | |
} | |
$calendar=new MyImaginaryCalendar(); | |
$finder=new MyCalendarFinder($calendar); | |
$dayNumber=$finder->dayOfTheWeek(2013, 11, 17); | |
printf('Hooray, got %s', $calendar->getDayName($dayNumber)); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
class MyCalendarFinder implements ImaginaryCalendarFinderInterface | |
{ | |
/** @var ImaginaryCalendarInterface */ | |
protected $calendar; | |
/** @param ImaginaryCalendarInterface $calendar */ | |
public function __construct(ImaginaryCalendarInterface $calendar) | |
{ | |
$this->calendar=$calendar; | |
} | |
/** | |
* @param int $year | |
* @param int $month | |
* @param int $day | |
* @return int | |
*/ | |
public function dayOfTheWeek($year, $month, $day) | |
{ | |
// get the blueprints | |
$daysInWeek = $this->calendar->getDaysOfTheWeek(); | |
$months = $this->calendar->getMonthsAndDaysCount(); | |
// first current day is the first day of the week | |
$currentDayOfTheWeek = array_keys($daysInWeek)[0]; | |
$firstDayOfTheWeek = $currentDayOfTheWeek; | |
$lastDayOfTheWeek = array_keys($daysInWeek)[count($daysInWeek)-1]; | |
// go each year | |
for ($iYear=0; $iYear <= $year; $iYear++) { | |
// each month | |
foreach ($months as $iMonth => $iMonthDays) { | |
// if leap year modify day count | |
if ($this->calendar->isLeapYear($iYear)) { | |
$iMonthDays=$this->calendar->getDaysInMonthOfLeapYear($iMonth, $iMonthDays); | |
} | |
// each day of the month | |
for ($iDay=1; $iDay <= $iMonthDays; $iDay++) { | |
// if method is satisfied | |
if ($year == $iYear && $month == $iMonth && $day == $iDay) { | |
return $currentDayOfTheWeek; | |
} | |
// move to the next day of the week | |
if ($currentDayOfTheWeek === $lastDayOfTheWeek) { | |
$currentDayOfTheWeek = $firstDayOfTheWeek; | |
} else { | |
++$currentDayOfTheWeek; | |
} | |
} | |
} | |
} | |
throw new Exception('Loop seems invalid'); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
class MyImaginaryCalendar implements ImaginaryCalendarInterface | |
{ | |
/** | |
* @return string | |
*/ | |
public function getDayName($day) | |
{ | |
return $this->getDaysOfTheWeek()[$day]; | |
} | |
/** | |
* @return array | |
*/ | |
public function getDaysOfTheWeek() | |
{ | |
$dayIndexes=[1,2,3,4,5,6,7]; | |
$dayNames=['Monday','Tuesday','Wednesday','Thursday','Friday','Saturday','Sunday']; | |
return array_combine($dayIndexes, $dayNames); | |
} | |
/** | |
* @return bool | |
*/ | |
public function isLeapYear($year) | |
{ | |
return $year % 5 == 0; | |
} | |
/** | |
* @return int | |
*/ | |
public function getDaysInMonthOfLeapYear($month, $days) | |
{ | |
if ($month == 13) { | |
return $days - 1; | |
} | |
return $days; | |
} | |
/* | |
* @return array | |
*/ | |
public function getMonthsAndDaysCount() | |
{ | |
$months=[1,2,3,4,5,6,7,8,9,10,11,12,13]; | |
$days=[22,21,22,21,22,21,22,21,22,21,22,21,22]; | |
return array_combine($months, $days); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment