## IntroductionHandling dates isn't trivial. Here, we implement an API for the Gregorian Calendar. This isn't helpful for calculating when Chinese New Year, Passover, or Ramadan falls, but for most purposes it will suffice. The sources of complexity in the Gregorian calendar are in determining whether a given year is leap, and the different month lengths. To simplify matters, we begin the calendar at a date
(the In the C library time.h, months start at 0 and days of the month start at 1. That is brain-damaged. Here, we will follow the ISO date convention. Months and days of the month both start at 1. Days of the week also start at 1 (Monday). Names of months and days of the week can be returned simply by array look-up. ## Data TypesFirst, we define ## FunctionsA leap year is divisible by 4, unless it's divisible
by 100 but not 400. To make the code clearer, we first define
a We can now define The number of days depends on whether the year is leap. The number of days before any month before March is the
the same in any year. From March onwards, it's one more if the year is
leap. The vector supplied to
The inputs of The first value in the loop is a year, initially set to
The day of the week is just the remainder of the number
of days since the start of In 2016, Easter falls on March 27th. It is, of course,
a Sunday. The code in the sandbox outputs the number of days since
## Bell, Book, and CandleDetermining the date on which Easter falls in a given year has always been problematic. At one point, an entire branch of the early Christian Church was threatened with excommunication over of a disagreement about how to calculate it. Computus, the algorithm currently used, is quite hairy and practically incomprehensible. Even Gauss got it wrong. There have been recent attempts to introduce a simpler mechanism. In principle, the rule for calculating Easter
is quite simple: Easter falls on the Sunday after the full moon
after the vernal equinox, which close to First, we write a simple helper function to calculate the difference between the value and the closest integer not higher than it. The synodic month (i.e. the time between a given phase and
the next occurrence of it) varies only slightly, and averages
Given a day of the week (the first argument) and an index (the second argument), the next index after the day of the week is obtained by iteration, starting one day after the second argument, until the day of the week is equal to the first argument. The day after a given lunar phase is tricky because phases
wrap around to
© Copyright Donald Fisk 2016 |