Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Method to Calculate the Day of the Week for All Dates 1905-2099

115 views
Skip to first unread message

Hans Lachman

unread,
Sep 9, 2009, 4:23:14 AM9/9/09
to
METHOD TO CALCULATE THE DAY OF THE WEEK FOR ALL DATES 1905-2099
- by Hans Lachman, 2009/09/09


This is a convenient method to calculate the day of the week
using an ordinary calculator and only a few simple formulas.


STEP 1. Calculate MonthIndex:

Month * 2.56 + 93

and then drop the fraction, and drop the hundreds digit, if any
(e.g., 123.72 becomes 23). So we have an integer less than 100.


STEP 2. With YLLD meaning "Year of Last Leap Day" (year during
which the last leap day occured, prior to the day in question),
calculate:

YLLD / 4 + Year + MonthIndex + Day

and then divide the result by 7.


STEP 3. Take the first digit of the decimal part (if none, use
zero), and map that to a day using the following pattern:

+-----+-----+-----+
| Sat | Sun | |
| 7 | 8 | 9 |
+-----+-----+-----+
| Thu | Fri | |
| 4 | 5 | 6 |
+-----+-----+-----+
| Tue | Wed | |
| 1 | 2 | 3 |
+-----+-----+-----+
| Mon |
| 0 |
+-----+


WAYS TO HELP YOU REMEMBER THE FORMULA:

2.56: 256 is a power of 2 (just add a dot).
93: 9 is 3 squared.
0=Mon: "Mon" has an "o" in it.

As for YLLD, it helps to be able to remember what numbers are
divisible by 4 (e.g., US election years). (For early 1904 and
prior, the method is off because the last leap year was 1896.)
Sometimes YLLD is the same as the year in question (see below).

The formula and constants may also be easier to remember if you
know why they are used. Most months start 2 or 3 days later in
the week cycle than the previous month, so we multiply by 2.56
to get the day-of-week offset caused by each month. Then, we
can discard the fraction, but we also need the "plus 93, mod
100" to compensate for Feb. being a short month. (Of course,
you could eliminate Step 1 by keeping a list of MonthIndex
values or their "mod 7" equivalents.) The use of the keypad as
a visual aid in Step 3 is a shortcut for calculating "mod 7."


EXAMPLE 1. December 31, 1999.

12 * 2.56 + 93 = 123.72 (MonthIndex = 23)
YLLD = 1996
1996 / 4 + 1999 + 23 + 31 = 2552
Divide by 7 = 364.571428..., first decimal = 5
Day of Week = Fri


EXAMPLE 2. February 29, 2000.

2 * 2.56 + 93 = 98.12 (MonthIndex = 98)
YLLD = 1996
1996 / 4 + 2000 + 98 + 29 = 2626
Divide by 7 = 375.142857..., first decimal = 1
Day of Week = Tue


EXAMPLE 3. March 1, 2000.

3 * 2.56 + 93 = 100.68 (MonthIndex = 0)
YLLD = 2000
2000 / 4 + 2000 + 0 + 1 = 2501
Divide by 7 = 357.285714..., first decimal = 2
Day of Week = Wed


This method was designed to minimize the number of constants and
formulas to remember, to minimize the number of steps to be
performed on a calculator, and to avoid conditional branches, in
order to be as easy and efficient as possible when the only
resources are your memory and a calculator.

This information is posted on the web (oz.ccnet.us/dayofweek).
If you have any comments, you may contact me there or via email.

Regards,
Hans Lachman
web: oz.ccnet.us
At yahoo Dot com: ccnetbox Dash gg09
(if all else fails, try the ccnet.us domain admin)

Hans Lachman

unread,
Sep 11, 2009, 2:59:13 AM9/11/09
to
[Note: This revision uses the constant 94 and 0=Sun, and adds
some clarifications. Please post comments, if any, to Usenet
sci.math, or send them to me. Thanks.]


METHOD TO CALCULATE THE DAY OF THE WEEK FOR ALL DATES 1905-2099

- by Hans Lachman, 2009/09/09, last edit 2009/09/10


This is a convenient method to calculate the day of the week
using an ordinary calculator and only a few simple formulas.


STEP 1. Calculate MonthIndex:

Month * 2.56 + 94

and then drop the fraction, and drop the hundreds digit, if any

(e.g., 124.72 becomes 24). So we have an integer less than 100.


STEP 2. With YLLD meaning "Year of Last Leap Day" (year during

which the last leap day occured, prior to the day in question;
YLLD therefore changes after each leap day), calculate:

YLLD / 4 + Year + MonthIndex + Day

and then divide the result by 7.


STEP 3. Take the first digit of the decimal part (if none, use
zero), and map that to a day using the following pattern:

+-----+-----+-----+
| Fri | Sat | |
| 7 | 8 | 9 |
+-----+-----+-----+
| Wed | Thu | |
| 4 | 5 | 6 |
+-----+-----+-----+
| Mon | Tue | |
| 1 | 2 | 3 |
+-----+-----+-----+
| Sun |
| 0 |
+-----+


WAYS TO HELP YOU REMEMBER THE FORMULA:

2.56: 256 is a power of 2 (just add a dot).

94: 9 and 4 are both perfect squares.
0=Sun: The sun is a big round thing.

As for YLLD, it helps to be able to remember what numbers are
divisible by 4 (e.g., US election years). (For early 1904 and
prior, the method is off because the last leap year was 1896.)
Sometimes YLLD is the same as the year in question (see below).

The formula and constants may also be easier to remember if you
know why they are used. Most months start 2 or 3 days later in
the week cycle than the previous month, so we multiply by 2.56
to get the day-of-week offset caused by each month. Then, we

can discard the fraction, but we also need the "plus 94, mod


100" to compensate for Feb. being a short month. (Of course,
you could eliminate Step 1 by keeping a list of MonthIndex
values or their "mod 7" equivalents.) The use of the keypad as
a visual aid in Step 3 is a shortcut for calculating "mod 7."


EXAMPLE 1. December 31, 1999.

12 * 2.56 + 94 = 124.72 (MonthIndex = 24)
YLLD = 1996
1996 / 4 + 1999 + 24 + 31 = 2553
Divide by 7 = 364.714285..., first decimal = 7


Day of Week = Fri


EXAMPLE 2. February 29, 2000.

2 * 2.56 + 94 = 99.12 (MonthIndex = 99)
YLLD = 1996
1996 / 4 + 2000 + 99 + 29 = 2627
Divide by 7 = 375.285714..., first decimal = 2


Day of Week = Tue


EXAMPLE 3. March 1, 2000.

3 * 2.56 + 94 = 101.68 (MonthIndex = 1)
YLLD = 2000
2000 / 4 + 2000 + 1 + 1 = 2502
Divide by 7 = 357.428571..., first decimal = 4


Day of Week = Wed


This method was designed to be as easy as possible to remember
and use when the only resources are your memory and an ordinary
calculator (meaning no tables or formulas stored on paper or
electronically, no mental arithmetic, no conditional branches,
minimal constants to remember, and minimal key-clicks).

Dave

unread,
Sep 11, 2009, 10:50:41 AM9/11/09
to

Why not use Zeller's Congruence. See http://en.wikipedia.org/wiki/Zeller%27s_congruence

Dave

Frederick Williams

unread,
Sep 11, 2009, 1:47:19 PM9/11/09
to
Hans Lachman wrote:

> minimal constants to remember,

What does that mean? Small constants or few of them?

--
Which of the seven heavens / Was responsible her smile /
Wouldn't be sure but attested / That, whoever it was, a god /
Worth kneeling-to for a while / Had tabernacled and rested.

Hans Lachman

unread,
Sep 12, 2009, 12:59:48 AM9/12/09
to
Thanks for the responses:

On Sep 12, 1:47 am, Frederick Williams <frederick.willia...@tesco.net>
wrote:


> Hans Lachman wrote:
> > minimal constants to remember,
>
> What does that mean?  Small constants or few of them?

Both. I originally had "few" in mind, but small
(i.e., compact) is also good because, for example,
one 12-digit number would probably be harder
for me to remember than, say, two numbers of
2 or 3 digits each.

On Sep 11, 10:50 pm, Dave <dave_and_da...@Juno.com> wrote:
> Why not use Zeller's Congruence. See
>http://en.wikipedia.org/wiki/Zeller%27s_congruence

I find that method to be harder to remember.
But I can understand that some might find
that method easier to remember than mine.
I suppose it's subjective. Regards,
/hans

Adam

unread,
Sep 15, 2009, 8:41:01 PM9/15/09
to
On Fri, 11 Sep 2009 07:50:41 -0700 (PDT), Dave wrote:

>Why not use Zeller's Congruence. See http://en.wikipedia.org/wiki/Zeller%27s_congruence

Because it's easy to do it wrong:

http://www.merlyn.demon.co.uk/zeller-c.htm#EI
Likely Errors in Implementations

Dave

unread,
Sep 15, 2009, 8:59:30 PM9/15/09
to
On Sep 15, 7:41 pm, Adam <n...@spam.edu> wrote:
> On Fri, 11 Sep 2009 07:50:41 -0700 (PDT), Dave wrote:
> >Why not use Zeller's Congruence. Seehttp://en.wikipedia.org/wiki/Zeller%27s_congruence

>
> Because it's easy to do it wrong:
>
> http://www.merlyn.demon.co.uk/zeller-c.htm#EI
> Likely Errors in Implementations

It's also easy to do it right, since the right way to implement it in
software is spelled out quite clearly.

Dave

lac...@ebony.ppc.ubc.ca

unread,
Mar 31, 2010, 9:12:52 PM3/31/10
to

TEXAS TWO-STEP CALCULATION OF THE WEEKDAY FOR ALL DAYS 00040301-42461231
- using Hans Lachman's Method of Congruence as optimised below -


Strictly adhering to Lachman's Maxim (Complexity is a diseconomy of scale),
this method was designed to run sublimely as a stand-alone function, when
your only recourse is to call a 68k ASM program via AMS on TI calculators:
i.e. no values looked up in tables, files or libraries when executing, no
kernel, no system calls, no exception processing, minimal registers to be
used, nor the need to save any. It is valid for (historical) Julian dates
as of 1.iii.IV and for Gregorian ones from 1.iii.MCM to 29.ii.MMCC.

Although using a processor more sophisticated than found on four-function
calculators, this method is simpler to execute than Hans' original Method
of Congruence needing manipulation of data by numerically competent users.
It succeeds where other Methods do not when computing the day of the week
even on the lowliest 68k device: having no need of extra instructions for
data stored in tables as in Babwani's Method nor for redundant operations
as in Zeller's or Tondering's; yet executing in less than two dozen lines.


The function below returns the corresponding ISO-compatible weekday number,
when called with 3 inputs loaded from the following locations:

; WDN, an address for storing result d0
; FLAG, to choose between sets of calendars (93 or 94 here)
; DATE, basic ISO format YYYYMMDD date-stamp as binary word&byte&byte
;
movem.l DATE,d0,d2
move.l FLAG,d1
lea WDN,a0
;
; APPLY STEP 1 OF HANS LACHMAN'S METHOD OF CONGRUENCE
andi.l #$0000ff00,d2
divu #100,d2
add.w d2,d1
divu #100,d1
swap d1 ; D1.W CONTAINS THE MonthIndex
;
; APPLY STEP 2
move.l d0,d2
add.b d2,d1
swap d2
add.w d2,d1
subi.l #$00000300,d0
movi.l #$00000012,d2
lsr d2,d0
add.w d1,d0
divu #7,d0
swap d0 ; D0.W CONTAINS THE WEEKDAY NUMBER
;
; RETURN THE WEEKDAY NUMBER TO LOCATION WDN
move.b d0,(a0)
rts
;
; Days of the week correspond to weekday numbers as:
; Sun=0 Mon=1 Tue=2 Wed=3 Thu=4 Fri=5 Sat=6

The code is streamlined such that parameters are to be passed to it in
proper format. For example, one must pass a flag of 94 for Gregorian
dates as of 1.iii.MCM until 29.ii.MMC, and 93 from 1.iii.MMC until
29.ii.MMCC; as well as 93 for (historical) Julian dates where years
start on 1.i, and years divisible by 4 are leap years. Some historians
claim that IV A.D. was not a leap year, so that a flag of 93 thereby
applies for Julian dates only as of 1.iii.IV. It applies till Julian
29.ii.MCM--a valid date for Orthodox countries like Russia & Greece.
This function thereby gives compleat valid historical continuity of
date conversion for SOMEWHERE on the planet for all days from 1.iii.IV
to 29.ii.MMCC. Otherwise, it still gives valid conversions for Julian
dates on the Orthodox calendar until 31.xii.MMMMCCXLVI A.D.

--

REFERENCES

http://oz.ccnet.us/dayofweek/
http://www.guernsey.net/~sgibbs/roman.html
http://en.wikipedia.org/wiki/Zeller%27s_congruence
http://www.tondering.dk/claus/cal/node3.html#SECTION00360000000000000000
babwani-congruence.blogspot.com/search/label/Frequently%20Asked%20Questions


osmium

unread,
Apr 1, 2010, 6:00:12 AM4/1/10
to

lac...@ebony.ppc.ubc.ca

unread,
Apr 3, 2010, 9:39:48 PM4/3/10
to
[N. B.: This revision uses the constant 94 and 0=Sun, and adds
further parameters to cover all valid Gregorian dates. Please
post comments, if any, via Usenet or via ccnet. Thanks.]

HOW TO CALCULATE THE DAY OF THE WEEK FOR DATES AS OF 15.x.1582
based on Hans' No-Sweat 1-Off 2-Fold 3-Step 4-Function Calculator Method

This is a more involved method to calculate the day of the week
for Gregorian calendar dates from 15.x.1582 and as far into the
future as workable using standard four-function calculators and
certain mobile phones via a generalised formula requiring fewer
key-clicks than any previous method not using tables.

Given:

Day.Month.Year as a Date on the Gregorian calendar as of
15.octob.1582
&
YLJLD as the 'Year in which the Last Julian Leap Day occurred' prior to
the given Date as if for a Julian Calendar whose years begin on 1.jan.
&
delta = Year - YLJLD
&
Century as a nominal "age" for each hundred of years as of 1.march.XY00
(only one lag Offset thereby required for an entire Gregorian Century)
so that if YLJLD = XYQR, then Century = XY (starting with Century 15)
&
yljld as the last two digits of XYQR, such that yljld = QR
&
under as the number of years that Century is less than the next higher
multiple of 4;

one can convert the given Date into a day of the week after completing
the 3 steps below--with 33 key-clicks or less, without any mental
multiplication or division.


STEP 0. Calculate the lag Offset:

under * 2

Remember the result or store it in memory.


STEP 1. Calculate the given Date's MonthIndex:

Month * 2.56 + 94

and then drop the fraction, and the hundreds digit, if any,
to get an integer less than 100, e.g. 124.72 becomes 24;
remember the result for use in Step 2.


STEP 2. Apply the generalised date conversion formula:

(yljld/.8 + delta + MonthIndex + Day + Offset) / 7


STEP 3. Apply Hans' keypad mapping:

Take the first digit after the decimal point (if none, use 0)
and map that to a day using the following patterns:

+-----+-----+-----+ +-----+-----+-----+
| Fri | Sat | | | 1 | 2 | 3 |
| 7 | 8 | 9 | | Mon | Tue | |
+-----+-----+-----+ +-----+-----+-----+


| Wed | Thu | | | 4 | 5 | 6 |

| 4 | 5 | 6 | | Wed | Thu | |
+-----+-----+-----+ +-----+-----+-----+
| Mon | Tue | | | 7 | 8 | 9 |
| 1 | 2 | 3 | | Fri | Sat | |
+-----+-----+-----+ +-----+-----+-----+
| Sun | | 0 |
| 0 | | Sun |
+-----+ +-----+

(This is equivalent to assigning days to remainders of divisions by 7
as for: Sun=0 Mon=1 Tue=2 Wed=3 Thu=4 Fri=5 Sat=6.)


Lag is the number of days that a Gregorian date to be converted falls before
the same Julian date. It was zero for Century 02, during which the Gregorian
Calendar, if already implemented beforehand, would have been the same as the
Julian--thus leading to Hans' Julian Step 2 formula. It must be decreased by
1 for every March 1st preceded by February 29th in the Julian but not in the
Gregorian calendar. Lag is now -13 and will be -14 as of 1.iii.MMC to start
off Century 21 when Hans' shorter Julian formula applies again to Gregorian
dates, the last time being in Centuries 11 & 12 when it was -7 in both. In
Century 00 as of 1.iii.IV, it was +2.


EXAMPLE Z. 29.Feb.1904 Century = 19 yljld = 00 delta = 4 under = 1

1 * 2 = 2


2 * 2.56 + 94 = 99.12 (MonthIndex = 99)

00/.8 + 4 + 99 + 29 + 2
Divide by 7 = 19.142857...
first decimal = 1 Day of Week = Mon


EXAMPLE A. 31.Dec.2100 Century = 21 yljld = 00 delta = 0 under = 3

3 * 2 = 6


12 * 2.56 + 94 = 124.72 (MonthIndex = 24)

00/.8 + 0 + 24 + 31 + 6
Divide by 7 = 8.714285...


first decimal = 7 Day of Week = Fri


EXAMPLE B. 29.Feb.2000 Century = 19 yljld = 96 delta = 4 under = 1

1 * 2 = 2


2 * 2.56 + 94 = 99.12 (MonthIndex = 99)

96/.8 + 4 + 99 + 29 + 2
Divide by 7 = 36.285714...


first decimal = 2 Day of Week = Tue


EXAMPLE C. 1.Mar.2000 Century = 20 yljld = 00 delta = 0 under = 4

4 * 2 = 8
3 * 2.56 + 94 = 101.28 (MonthIndex = 1)
00/.8 + 0 + 1 + 1 + 8
Divide by 7 = 1.428571...


first decimal = 4 Day of Week = Wed


The Examples above are for a standard (running total) calculator;
those for RPN or algebraic calculators are left as an exercise.

(Hint: re-order Steps and streamline operations.)

--

REFERENCES: http://oz.ccnet.us/dayofweek/

http://groups.google.com/group/sci.math/msg/a716e5ca3af3ed28

Milton Lachman

unread,
Apr 1, 2011, 11:18:12 AM4/1/11
to
TEXAS 2-STEP 2.0 TO CALCULATE THE DAY OF THE WEEK AS OF 1582 TO 2Y2K2
- via transmogrification of Hans Lachman's Method of Congruence -


Strictly adhering to Lachman's Maxim (Complexity is a diseconomy of scale)

a reworking of Hans' Method has been coded as a stand-alone function when


your only recourse is to call a 68k ASM program via AMS on TI calculators:
i.e. no values looked up in tables, files or libraries when executing, no
kernel, no system calls, no exception processing, minimal registers to be

used, nor the need to save any. It is for valid Gregorian dates from 1582,
as of the Ides of October, to 4004 A.D.

Although using as unsophisticated a processor as a 68k on programmable TI
calculators, this reworking of Hans' Method is more efficient than others.
It succeeds where other methods do not when computing the day of the week


even on the lowliest 68k device: having no need of extra instructions for
data stored in tables as in Babwani's Method nor for redundant operations

as in Zeller's or Tondering's--nor even a C compiler running on a bloated
development system as in Mike Keith's--yet executing in less than 2 dozen
operations, and needing just 2 registers.

The function below returns the corresponding ISO-compatible weekday number

when called with 2 inputs loaded from the following 2 locations:

; WDN, an address for storing result d0

; DATE, basic ISO-format date-stamp cymd as 2 pairs of base-100 bytes
;
movem.l DATE,d1,d2
;
; STEP 1
andi.l #$f00,d1
divu #100,d1
add.w #$7a,d1
andi.l #$7f,d1 ; Month Index
;
; STEP 2
add.b d2,d1
swap d2
add.b d2,d1
swap d2
subi.l #$300,d2
lsl #6,d2
rol #3,d2
addq.b #8,d1
sub.b d2,d1
movi.l #27,d0
lsr d0,d2
add.b d1,d2 ; QRdiv4 + y + MI + d + under+under
;
divu #7,d2
swap d2 ; D2.W BECOMES THE WEEKDAY NUMBER


;
; RETURN THE WEEKDAY NUMBER TO LOCATION WDN

move.b d2,WDN


rts
;
; Days of the week correspond to weekday numbers as:

; Sun=0 Mon=1 Tue=2 Wed=3 Thu=4 Fri=5 Sat=6

Inputs are to be passed in the proper format:
No component of a Date may be passed as a pair of base 10 nibbles.

--

REFERENCES

http://oz.ccnet.us/dayofweek/
http://www.guernsey.net/~sgibbs/roman.html
http://www.merlyn.demon.co.uk/zel-like.htm#Keith
http://www.tondering.dk/claus/cal/node3.html#SECTION00360000000000000000
babwani-congruence.blogspot.com/search/label/Frequently%20Asked%20Questions


Milton Lachman

unread,
Apr 21, 2011, 5:41:03 PM4/21/11
to
[This immanently transcendent emanation for Good Freya-
day is singularly in want of April Fools' Easter eggs]

TEXAS 2-STEP 2.2 TO CALCULATE THE DAY OF THE WEEK AS OF 1582 TO 2Y2K2
- via transfiguration of Hans Lachman's Method of Congruence -


Strictly adhering to Lachman's Maxim (Complexity is a diseconomy of scale)
a reworking of Hans' Method has been coded as a stand-alone function when
your only recourse is to call a 68k ASM program via AMS on TI calculators:
i.e. no values looked up in tables, files or libraries when executing, no
kernel, no system calls, no exception processing, minimal registers to be
used, nor the need to save any. It is for valid Gregorian dates from 1582,
as of the Ides of October, to 4004 A.D.

Although using as unsophisticated a processor as a 68k on programmable TI
calculators, this reworking of Hans' Method is more efficient than others.
It succeeds where other methods do not when computing the day of the week
even on the lowliest 68k device: having no need of extra instructions for
data stored in tables as in Babwani's Method nor for redundant operations
as in Zeller's or Tondering's--nor even a C compiler running on a bloated
development system as in Mike Keith's--yet executing in less than 2 dozen
operations, and needing just 2 registers.

The function below returns the corresponding ISO-compatible weekday number
when called with 2 inputs loaded from the following 2 locations:

; WDN, an address for storing result d2
; DATE, basic ISO-format date-stamp CYmd as 2 pairs of base-10^2 bytes
;
movem.l DATE,d1,d2


;
; APPLY STEP 1 OF HANS LACHMAN'S METHOD OF CONGRUENCE

andi.l #$f00,d1
divu #100,d1
add.w #94,d1
andi.l #$ff,d1
divu #100,d1 ; Month Index
;
; STEP 2
add.l d2,d1
swap d1
add.b d2,d1


subi.l #$300,d2
lsl #6,d2
rol #3,d2
addq.b #8,d1
sub.b d2,d1

lsr #7,d2
lsr #7,d2
lsr #7,d2
lsr #6,d2
add.w d1,d2 ; QRdiv4 + Y + MI + d + under+under

Milton Lachman

unread,
May 1, 2011, 5:48:28 PM5/1/11
to
[The code in this version for Beltane intertwines that from the
bogus versions for April Fools' & Good Freyaday (each one using
a different approach) and implements the approach as posted for
four-function calculators. The eminently more suitable code for
the digital approach of the 2.0 kind is left for avid coders to
figure out for themselves.]


TEXAS 2-STEP 2.2 TO CALCULATE THE DAY OF THE WEEK AS OF 1582 TO 2Y2K2

- via an elaboration of Hans Lachman's Method of Congruence -


Strictly adhering to Lachman's Maxim (Complexity is a diseconomy of scale)
a reworking of Hans' Method has been coded as a stand-alone function when
your only recourse is to call a 68k ASM program via AMS on TI calculators:
i.e. no values looked up in tables, files or libraries when executing, no
kernel, no system calls, no exception processing, minimal registers to be
used, nor the need to save any. It is for valid Gregorian dates from 1582,
as of the Ides of October, to 4004 A.D.

Although using as unsophisticated a processor as a 68k on programmable TI
calculators, this reworking of Hans' Method is more efficient than others.
It succeeds where other methods do not when computing the day of the week
even on the lowliest 68k device: having no need of extra instructions for
data stored in tables as in Babwani's Method nor for redundant operations
as in Zeller's or Tondering's--nor even a C compiler running on a bloated
development system as in Mike Keith's--yet executing in less than 2 dozen
operations, and needing just 2 registers.

The function below returns the corresponding ISO-compatible weekday number
when called with 2 inputs loaded from the following 2 locations:

; WDN, an address for storing result d2
; DATE, basic ISO-format date-stamp CYmd as 2 pairs of base-10^2 bytes
;
movem.l DATE,d1,d2
;

; APPLY STEP 1 (HANS LACHMAN'S METHOD OF CONGRUENCE)


andi.l #$f00,d1
divu #100,d1
add.w #94,d1
andi.l #$ff,d1
divu #100,d1 ; Month Index
;
; STEP 2
add.l d2,d1
swap d1
add.b d2,d1
subi.l #$300,d2
lsl #6,d2
rol #3,d2
addq.b #8,d1
sub.b d2,d1
lsr #7,d2
lsr #7,d2
lsr #7,d2
lsr #6,d2

add.b d1,d2 ; QRdiv4 + Y + MI + d + under+under

lac...@ebony.ppc.ubc.ca

unread,
Feb 2, 2012, 12:40:38 PM2/2/12
to

Or, for the less avid, they can ferret it out for themselves at:

gopher://gopherite.org/1/users/lachman/TemporalRetrology/68k/

Happy Groundhog Day!

lachman wrote:
[ . . . The eminently more suitable code for the digital approach of
the 2.0 kind is left for avid coders to figure out for themselves.]


TEXAS 2-STEP 2.2 TO CALCULATE THE DAY OF THE WEEK AS OF 1582 TO 2Y2K2
- via an elaboration of Hans Lachman's Method of Congruence -

--

Charles Richmond

unread,
Feb 4, 2012, 3:50:52 AM2/4/12
to
<lac...@ebony.ppc.ubc.ca> wrote in message
news:jgehql$hr1$1...@odin.sdf-eu.org...
>
> Or, for the less avid, they can ferret it out for themselves at:
>
> gopher://gopherite.org/1/users/lachman/TemporalRetrology/68k/
>
> Happy Groundhog Day!
>
> lachman wrote:
> [ . . . The eminently more suitable code for the digital approach of
> the 2.0 kind is left for avid coders to figure out for themselves.]
>

To calculate the day of the week for *any* date in the Gregorian Calendar,
you can use Zeller's Congruence:

http://en.wikipedia.org/wiki/Zeller%27s_congruence

Here is a function in C that I wrote to do this. Changing it to 68k
assembly should be straightforward:

int weekday(day,month,year) /* find the day of week from */
int day, month, year; /* day, month, and year */
{ /* Sunday..Saturday is
0..6 */
int index, yrndx, mondx;

if(month <= 2) { /* Jan or Feb month adjust */
month += 12;
year--;
}

yrndx = year + (year/4) - (year/100) + (year/400);
mondx = (2 * month) + (3 * (month + 1)) / 5;
index = day + mondx + yrndx + CONST;

return(index % 7);
}


--
+<><><><><><><><><><><><><><><><><><><>+
| Charles Richmond nume...@aquaporin4.com |
+<><><><><><><><><><><><><><><><><><><>+

Dr J R Stockton

unread,
Feb 5, 2012, 5:13:27 PM2/5/12
to
In sci.math message <jgirhd$ie2$1...@dont-email.me>, Sat, 4 Feb 2012
02:50:52, Charles Richmond <net...@aquaporin4.com> posted:
OK at first sight, except that CONST appears undefined. By varying it
one should be able to number the days of the week with any chosen day
being zero. Make Monday so, add 1, and you have the ISO numbering.

Some implementations written & "tested" before AD 2000 fail where mod-
of-negative is taken for some dates early in a century; but yours looks
OK. Zeller understood the possibility.

Zeller's relevant papers & Card, imaged and translated, can be found via
<http://www.merlyn.demon.co.uk/undex.htm#dat> subsection 2.9.

For 1901 to 2099, the 100 & 400 terms can be omitted, if CONST is
correspondingly adjusted.

Zeller also did Easter code, OK in the papers but wrong in the Card.

--
(c) John Stockton, nr London, UK. ?@merlyn.demon.co.uk Turnpike v6.05.
Website <http://www.merlyn.demon.co.uk/> - w. FAQish topics, links, acronyms
PAS EXE etc. : <http://www.merlyn.demon.co.uk/programs/> - see in 00index.htm
Dates - miscdate.htm estrdate.htm js-dates.htm pas-time.htm critdate.htm etc.

Charles Richmond

unread,
Feb 6, 2012, 2:50:48 PM2/6/12
to
"Dr J R Stockton" <repl...@merlyn.demon.co.uk> wrote in message
news:JakN$7dH8v...@invalid.uk.co.demon.merlyn.invalid...
>
> [snip...] [snip...] [snip...]
>
> OK at first sight, except that CONST appears undefined. By varying it
> one should be able to number the days of the week with any chosen day
> being zero. Make Monday so, add 1, and you have the ISO numbering.
>

Yes, I failed to put the "#define" for CONST in there. The value should be
1 to have the day names fall as the comment promises.

> Some implementations written & "tested" before AD 2000 fail where mod-
> of-negative is taken for some dates early in a century; but yours looks
> OK. Zeller understood the possibility.
>
> Zeller's relevant papers & Card, imaged and translated, can be found via
> <http://www.merlyn.demon.co.uk/undex.htm#dat> subsection 2.9.
>

The URL works better if you spell "undex" as "index". :-) This web page
is linked to the Wikipedia site for Zeller himself.

> For 1901 to 2099, the 100 & 400 terms can be omitted, if CONST is
> correspondingly adjusted.
>
> Zeller also did Easter code, OK in the papers but wrong in the Card.
>

There is also good info in Wikipedia for calculating Easter and Orthodox
Easter, which often do *not* fall on the same Sunday. In one of the
problems at the end of a chapter in _Fundamental Algorithms_, Knuth
discusses the algorithm for calculating Easter.

Dr J R Stockton

unread,
Feb 6, 2012, 4:05:44 PM2/6/12
to
In sci.math message <ipkkfb$9u3$1...@speranza.aioe.org>, Sun, 1 May 2011
21:48:28, Milton Lachman <lac...@ebony.ppc.ubc.ca> posted:


> The function below returns the corresponding ISO-compatible weekday number
> when called with 2 inputs loaded from the following 2 locations:


> ; Days of the week correspond to weekday numbers as:
> ; Sun=0 Mon=1 Tue=2 Wed=3 Thu=4 Fri=5 Sat=6

That is only ISO 8601 compatible if Sundays are ignored; Sunday is ISO
Day 7. Subtract 1 (by altering a constant?) before divu #7,d2 and
add 1 after; or append something implementing Result or= 7 or else
if result = 0 then result = 7.

Since the Gregorian Calendar is by definition perpetual and immutable,
there is no need to apply an upper limit to the range until the
algorithm has a numeric overflow.

Since the Gregorian Calendar may be used proleptically, it would be nice
if the lower limit were the date 0000-01-01, which, as you may remember,
was a Saturday.

If your code works, or can be adjusted to work, for years 0000 to 0399
inclusive, then your code can be made perpetual by starting with
year = year mod 400.

Charles Richmond

unread,
Feb 7, 2012, 8:50:58 AM2/7/12
to
"Dr J R Stockton" <repl...@merlyn.demon.co.uk> wrote in message
news:THIb4oHo...@invalid.uk.co.demon.merlyn.invalid...
> In sci.math message <ipkkfb$9u3$1...@speranza.aioe.org>, Sun, 1 May 2011
> 21:48:28, Milton Lachman <lac...@ebony.ppc.ubc.ca> posted:
>
>
>> The function below returns the corresponding ISO-compatible weekday
>> number
>> when called with 2 inputs loaded from the following 2 locations:
>
>
>> ; Days of the week correspond to weekday numbers as:
>> ; Sun=0 Mon=1 Tue=2 Wed=3 Thu=4 Fri=5 Sat=6
>
> That is only ISO 8601 compatible if Sundays are ignored; Sunday is ISO
> Day 7. Subtract 1 (by altering a constant?) before divu #7,d2 and
> add 1 after; or append something implementing Result or= 7 or else
> if result = 0 then result = 7.
>

I was *not* worried about ISO 8601 compatibility. I wanted Sunday to be
zero, because arrays in C are zero-based. So the array of pointers to the
names of the days of the week... will have subscripts from 0 to 6.

> Since the Gregorian Calendar is by definition perpetual and immutable,
> there is no need to apply an upper limit to the range until the
> algorithm has a numeric overflow.
>
> Since the Gregorian Calendar may be used proleptically, it would be nice
> if the lower limit were the date 0000-01-01, which, as you may remember,
> was a Saturday.
>

I was *not* immediately aware that 0000-01-01 was a Saturday, but I know
that 0001-01-01 was a Monday. :-)

> If your code works, or can be adjusted to work, for years 0000 to 0399
> inclusive, then your code can be made perpetual by starting with
> year = year mod 400.
>

I am aware that the patterns of years repeat every 400 years, and that the
period between 401 through 800 inclusive contains an exact number of weeks.
(That would be 20,871 weeks to be exact.) And each one of the 400 year
periods beginning in 1, 401, 801, 1201, 1601, 2001, etc... all begin on a
Monday. Although the function given may *not* be perpetual, it works for
most years that one would reasonably expect to be checked.

Dr J R Stockton

unread,
Feb 7, 2012, 6:32:17 PM2/7/12
to
In sci.math message <jgpauq$fqi$1...@dont-email.me>, Mon, 6 Feb 2012
13:50:48, Charles Richmond <net...@aquaporin4.com> posted:


>There is also good info in Wikipedia for calculating Easter and
>Orthodox Easter, which often do *not* fall on the same Sunday. In one
>of the problems at the end of a chapter in _Fundamental Algorithms_,
>Knuth discusses the algorithm for calculating Easter.

I have in the past corrected that page.

Zeller did day-of-week and Easter Sunday for both the Julian and
Gregorian Calendars. Transferring Julian (Orthodox) Easter to the
Gregorian Calendar is simple; just allow for the changes to the secular
calendar made by the Papal Bull Inter Gravissimas.

Knuth is, no doubt, right - or mostly so; I see that in critdate.htm I
have
9006-04-20 Sun</tt> - First Easter date for which Knuth's code
has a problem with Epact :
<a href="http://www.sunvaley.com/TEMP/Formulas.pdf">J D McC</a>
But I do not know how traceable his algorithm is to true authority.

My own algorithm is traceably (as shown) derived from UK (and therefore
US) authority - the Prayer Book effectively reproduces the relevant
parts of the Calendar Act of 1751, as passed. It agrees with Knuth and
others for the full 5,700,000 year period, It also agrees with one -
possibly the slowest in captivity - in which I implemented in a literal
fashion the algorithm that Clavius wrote for Pope Gregory.

The older Prayer Book defines Julian Easter.

However, the UK algorithm is truly defined only to the year 8599 (but
there is no doubt about the extrapolation); and, although I have found
that part in Clavius, Clavius wrote about alternatives and I have not
managed to identify there a definitive statement of what should be used
past AD 4999.

If anyone here reads Latin ...

I also have code from Al Petrofsky which is correct, compact, and fast,
but has unexplained numbers in it.

Dr J R Stockton

unread,
Feb 8, 2012, 4:51:09 PM2/8/12
to
In sci.math message <jgra82$q6t$1...@dont-email.me>, Tue, 7 Feb 2012
07:50:58, Charles Richmond <net...@aquaporin4.com> posted:

>"Dr J R Stockton" <repl...@merlyn.demon.co.uk> wrote in message
>news:THIb4oHo...@invalid.uk.co.demon.merlyn.invalid...
>> In sci.math message <ipkkfb$9u3$1...@speranza.aioe.org>, Sun, 1 May 2011
>> 21:48:28, Milton Lachman <lac...@ebony.ppc.ubc.ca> posted:
>>
>>
>>> The function below returns the corresponding ISO-compatible weekday
>>>number
>>> when called with 2 inputs loaded from the following 2 locations:
>>
>>
>>> ; Days of the week correspond to weekday numbers as:
>>> ; Sun=0 Mon=1 Tue=2 Wed=3 Thu=4 Fri=5 Sat=6
>>
>> That is only ISO 8601 compatible if Sundays are ignored; Sunday is ISO
>> Day 7. Subtract 1 (by altering a constant?) before divu #7,d2 and
>> add 1 after; or append something implementing Result or= 7 or else
>> if result = 0 then result = 7.
>>
>
>I was *not* worried about ISO 8601 compatibility. I wanted Sunday to
>be zero, because arrays in C are zero-based. So the array of pointers
>to the names of the days of the week... will have subscripts from 0 to
>6.

But, as quoted, you asserted ISO compatibility.


>> Since the Gregorian Calendar is by definition perpetual and immutable,
>> there is no need to apply an upper limit to the range until the
>> algorithm has a numeric overflow.
>>
>> Since the Gregorian Calendar may be used proleptically, it would be nice
>> if the lower limit were the date 0000-01-01, which, as you may remember,
>> was a Saturday.
>>
>
>I was *not* immediately aware that 0000-01-01 was a Saturday, but I
>know that 0001-01-01 was a Monday. :-)

Y2K-day, 2000 years later, was a Saturday.

>> If your code works, or can be adjusted to work, for years 0000 to 0399
>> inclusive, then your code can be made perpetual by starting with
>> year = year mod 400.
>>
>
>I am aware that the patterns of years repeat every 400 years, and that
>the period between 401 through 800 inclusive contains an exact number
>of weeks. (That would be 20,871 weeks to be exact.) And each one of
>the 400 year periods beginning in 1, 401, 801, 1201, 1601, 2001, etc...
>all begin on a Monday. Although the function given may *not* be
>perpetual, it works for most years that one would reasonably expect to
>be checked.


Around 20 years ago, possibly 1993, I saw a draft RFC - I doubt whether
I still had it, but RFC 3339 of 2002 corresponds. It had C code,
derived from Zeller, for day-of-week. No doubt it had been tested, and
passed, with a selection of nearby dates, and perhaps to some extent for
other years. But, evidently, it had not been fully tested, since it
failed (mod of negative not giving desired result, for quite a few days
after 2000-02-29 and for fewer days in each following year until about
2019 (or similar; that's from memory).

Zeller knew about that :
<http://www.merlyn.demon.co.uk/zel-82px.htm>, page 313, section II,
Aufg. 1, Regel a, end, reads k/4 - 2e (od. + 5e)

and similarly in other papers.

With a computer, one might as well test comprehensively; this machine,
using Zeller's Easter code, does around four million years per second.

Microsoft VBScript DatePart is documented as giving ISO 8601 week
numbers. I dare say they tested it, to some extent. But it is wrong
for one day in three of each 28 consecutive "Julian-type" years, plus
one further day for each 400 years - details in my vb-date2.htm. As far
as I can tell, that code is still in current products, even though
there's been correct bug-fix code on their Web site for years
(appallingly bodged code; I've sent them much better code; no effect).

Charles Richmond

unread,
Feb 9, 2012, 9:48:02 AM2/9/12
to
"Dr J R Stockton" <repl...@merlyn.demon.co.uk> wrote in message
news:U6xKnaYN...@invalid.uk.co.demon.merlyn.invalid...
> In sci.math message <jgra82$q6t$1...@dont-email.me>, Tue, 7 Feb 2012
> 07:50:58, Charles Richmond <net...@aquaporin4.com> posted:
>
>>"Dr J R Stockton" <repl...@merlyn.demon.co.uk> wrote in message
>>news:THIb4oHo...@invalid.uk.co.demon.merlyn.invalid...
>>> In sci.math message <ipkkfb$9u3$1...@speranza.aioe.org>, Sun, 1 May 2011
>>> 21:48:28, Milton Lachman <lac...@ebony.ppc.ubc.ca> posted:
>>>
>>>
>>>> The function below returns the corresponding ISO-compatible weekday
>>>>number
>>>> when called with 2 inputs loaded from the following 2 locations:
>>>
>>>
>>>> ; Days of the week correspond to weekday numbers as:
>>>> ; Sun=0 Mon=1 Tue=2 Wed=3 Thu=4 Fri=5 Sat=6
>>>
>>> That is only ISO 8601 compatible if Sundays are ignored; Sunday is ISO
>>> Day 7. Subtract 1 (by altering a constant?) before divu #7,d2 and
>>> add 1 after; or append something implementing Result or= 7 or else
>>> if result = 0 then result = 7.
>>>
>>
>>I was *not* worried about ISO 8601 compatibility. I wanted Sunday to
>>be zero, because arrays in C are zero-based. So the array of pointers
>>to the names of the days of the week... will have subscripts from 0 to
>>6.
>
> But, as quoted, you asserted ISO compatibility.
>

Somehow the quoted text must have gotten mixed up... I did *not* say that my
function was ISO 8601 compatible. I was only marginally aware of ISO 8601
until you mentioned it. I just wanted something that *worked*. I have used
similar functions when writing PHP code to determine what day was the third
Thursday of the month... for reminders to be auto-posted for a club meeting.
Also I have used the weekday function to help calculated which weekend would
be the "spring forward" and "fall back" for daylight saving time.

>
>>> Since the Gregorian Calendar is by definition perpetual and immutable,
>>> there is no need to apply an upper limit to the range until the
>>> algorithm has a numeric overflow.
>>>
>>> Since the Gregorian Calendar may be used proleptically, it would be nice
>>> if the lower limit were the date 0000-01-01, which, as you may remember,
>>> was a Saturday.
>>>
>>
>>I was *not* immediately aware that 0000-01-01 was a Saturday, but I
>>know that 0001-01-01 was a Monday. :-)
>
> Y2K-day, 2000 years later, was a Saturday.
>

Yes, all of the year patterns repeat every 400 years.

lac...@ebony.ppc.ubc.ca

unread,
Feb 13, 2012, 6:04:52 PM2/13/12
to
>>"Dr J R Stockton" <repl...@merlyn.demon.co.uk> wrote
>>> In sci.math message <ipkkfb$9u3$1...@speranza.aioe.org>, Sun, 1 May 2011
>>> 21:48:28, Milton Lachman <lac...@ebony.ppc.ubc.ca> posted:
>>>> The function below returns the corresponding ISO-compatible weekday
>>>>number
>>>> ; Days of the week correspond to weekday numbers as:
>>>> ; Sun=0 Mon=1 Tue=2 Wed=3 Thu=4 Fri=5 Sat=6
>>>
>>> That is only ISO 8601 compatible if Sundays are ignored; Sunday is ISO
>>> Day 7.

Ought not Sunday = 0 be considered "backward-compatible"?
In keeping with other Easter/Beltane eggs hid in parody
posts to this thread, it might have said "ISO compliant,"
but that wouldn't have been hiding anything very well,
would it?


Dr J R Stockton

unread,
Feb 14, 2012, 4:19:00 PM2/14/12
to
In sci.math message <jhc4uj$i5r$1...@odin.sdf-eu.org>, Mon, 13 Feb 2012
23:04:52, lac...@ebony.ppc.ubc.ca posted:
Only if ISO 8601 were to give it as an allowable alternative, which it
does not.

However, in languages where arrays start ay zero, it can be useful to
provide the DoW TLAs as an array with elements
Sun Mon Tue Wed Thu Fri Sat Sun
so that both 0 & 7 find Sun.

Also, in JavaScript the DoW of a Date Object D can be obtained using
D.getDay() || 7
but note that a NaN date gives an ISO Sunday.
0 new messages