There are a bunch of general methods to do this listed on the Wikipedia page for Determination of the day of the week. Typically, there are several steps involved, and you need to memorize some small tables of numbers.
I used to practice that mental calculation (and many others) when I was about 16. Although all the steps are basic arithmetic, it’s not easy to do the calculation in your head in a couple of seconds. Given that most of these questions that you’re likely to face in day-to-day life will be about the current year, it seemed like it might be a poor tradeoff to learn the complicated method to calculate the day of the week for any date if there was a simpler way to do it for a specific year.
The method I came up with after that observation is really simple. It just requires you to memorize a single 12-digit sequence for the current year. The 12 digits correspond to the first Monday for each month.
For example, the sequence for 2012 is 265-274-263-153. Suppose you’ve memorized the sequence and you need to know the day of the week for March 29th. You can trivially calculate that it’s a Thursday. You take the 3rd digit of the sequence (because March is the 3rd month), which is 5. That tells you that the 5th of March was a Monday. Then you just go backward or forward as many weeks and days as you need. The 5th was a Monday, so the 12th, 19th, and 26th were too, which means the 29th was a Thursday.
It’s nice because the amount you need to memorize is small, and you can memorize less digits if you only want to cover a shorter period. The calculation is very simple and always the same in every case, and you never have to think about leap years. At the start of each year you just memorize a single sequence, which is quickly reinforced once you use it a few times.
Here’s Python code to print the sequence for any year.
import datetime, sys
year = int(sys.argv)
year = datetime.datetime.today().year
firstDayToFirstMonday = ['1st', '7th', '6th', '5th', '4th', '3rd', '2nd']
months = ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun',
'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec']
summary = ''
for month in range(12):
firstOfMonth = datetime.datetime(year, month + 1, 1).weekday()
firstMonday = firstDayToFirstMonday[firstOfMonth]
print months[month], firstMonday
summary += firstMonday
print 'Summary:', '-'.join(summary[x:x+3] for x in range(0, 12, 3))
The output for 2012 looks like
Jan 2nd Feb 6th Mar 5th Apr 2nd May 7th Jun 4th Jul 2nd Aug 6th Sep 3rd Oct 1st Nov 5th Dec 3rd Summary: 265-274-263-153
The memory task is made simpler by the fact that there are only 14 different possible sequences. Or, if you consider just the last 10 digits of the sequences (i.e., starting from March), there are only 7 possible sequences. There are only 14 different sequences, so if you use this method in the long term, you’ll find the effort of remembering a sequence will pay off when it re-appears. E.g., 2013 and 2019 both have sequence 744-163-152-742. There are other nice things you can learn that can also make the memorization and switching between years easier (see the Corresponding months section on the above Wikipedia page).
Here are the sequences through 2032:
2012 265-274-263-153 2013 744-163-152-742 2014 633-752-741-631 2015 522-641-637-527 2016 417-426-415-375 2017 266-315-374-264 2018 155-274-263-153 2019 744-163-152-742 2020 632-641-637-527 2021 411-537-526-416 2022 377-426-415-375 2023 266-315-374-264 2024 154-163-152-742 2025 633-752-741-631 2026 522-641-637-527 2027 411-537-526-416 2028 376-315-374-264 2029 155-274-263-153 2030 744-163-152-742 2031 633-752-741-631 2032 521-537-526-416