What Actually Makes a Year a Leap Year
A leap year happens when the Earth's orbit around the sun doesn't divide evenly into 365-day chunks. It takes about 365.2425 days, so every four years we tack on February 29th to keep the calendar from drifting. The Gregorian calendar rule set is straightforward on paper: divisible by 4, except divisible by 100 unless also divisible by 400. That exception clause is where most people lose track. I spent too many hours debugging date calculations for a scheduling system back when I was still early in my career. The problem wasn't figuring out what a leap year was. It was handling the edge cases across different calendar systems and timezone conversions. We had a production bug where a user in New Zealand was scheduled for a task on February 28th, but because their system handled the leap second and the 29th differently than the server, the task fired a day late. The fix was to stop using local timestamps for any cross-timezone scheduling and run everything through UTC with explicit date math libraries instead of rolling our own leap year logic. Nobody should do their own leap year math from scratch. Use an existing library.
List Of Leap Years And How To Generate One Programmatically
If you need a List Of Leap Years for a specific range, generating it is trivial once you know the rules. Here's the logic in pseudocode form: For each year Y in your range: if Y mod 4 equals 0 AND (Y mod 100 does not equal 0 OR Y mod 400 equals 0), then Y is a leap year. That's it. The century years throw people off because they seem like leap years by the "divisible by 4" rule, but 1900 wasn't a leap year, even though 2000 was. The difference is 1900 is divisible by 100 but not by 400. 2000 clears both thresholds.
For a practical example, here are the leap years in the 20th century: 1904, 1908, 1912, 1916, 1920, 1924, 1928, 1932, 1936, 1940, 1944, 1948, 1952, 1956, 1960, 1964, 1968, 1972, 1976, 1980, 1984, 1988, 1992, 1996. Note that 1900 itself is excluded. That single missing year causes errors in spreadsheets that blindly assume every fourth year counts.
Get the Full Details

Common Pitfalls When Working With Leap Year Data
One thing nobody warns you about is how spread sheets handle dates internally. Excel stores dates as serial numbers where day 1 is January 1, 1900. The bug here is historical: Excel inherited a Quattro Pro bug that treated 1900 as a leap year even though it isn't. So if you're pulling a List Of Leap Years from an Excel export, 1900 will show up as a leap year in your data. You have to strip it out manually or the whole downstream calculation is wrong by one day for anything before March 1, 1900. Another pitfall is the Julian-to-Gregorian transition. Different countries switched at different times. Britain and its colonies switched in 1752. France switched in 1582. Russia didn't switch until 1918. If you're working with historical data across multiple regions, the same calendar date can represent different actual days depending on where the record originated. This matters more than you'd think for genealogy work, legal documents, and anything involving ship manifests or court records from before the 20th century. If you're generating a large list programmatically, the fastest approach is a simple loop. For a range spanning 1,000 years, the loop completes in under a millisecond on modern hardware. The bottleneck is never the leap year calculation itself. It's the I/O when you're writing the output to a file or database. If you need a List Of Leap Years covering several centuries, batch-write in chunks of 10,000 rows at a time to avoid memory pressure on the connection.
When The Rules Break Down
Leap year rules work fine for civil timekeeping, but they don't account for the Earth's actual rotation slowing down. TheGregorian calendar adds a day roughly every 4 years, but the Earth's rotation is losing about 1.7 milliseconds per century to tidal friction. That means leap seconds get added occasionally to keep atomic time aligned with solar time. The last leap second was inserted at the end of 2016. There's been discussion about abolishing leap seconds entirely by 2035 because they cause subtle failures in banking and networking systems that assume time always moves forward uniformly. For most purposes, the standard Gregorian rules are sufficient. But if you're building something that needs to handle dates beyond the year 4000, you're already outside the scope of the current calendar system. The rule about divisibility by 400 keeps the calendar accurate to within one day every 3,300 years or so. Whether that precision matters depends on what you're calculating.