基姆拉尔森计算公式(Zeller's Congruence 的变体)是一种快速根据公历日期计算星期几的数学公式。其核心思想是通过对年月日的数值进行特定变换和取模运算,直接得到星期几的结果。
公式定义
对于日期 年-月-日
,公式如下:
其中:
-
月份调整:若月份为 1 月或 2 月,需视为上一年的 13 月或 14 月。例如,2024 年 1 月 1 日 → 视为 2023 年 13 月 1 日。
-
变量含义:
-
h: 星期(0=星期六, 1=星期日, 2=星期一, ..., 6=星期五)
-
d: 日(1-31)
-
m: 调整后的月份(3-14,对应原1-12月)
-
y: 调整后的年份的后两位(例如 2023 年 → 23)
-
c: 调整后的年份的前两位(例如 2023 年 → 20)
-
公式使用步骤
以 2024 年 8 月 15 日 为例:
通过此公式,无需逐日累加即可高效计算任意日期的星期,特别适合处理大时间跨度的日期问题。
-
调整月份和年份:
-
原日期:2024 年 8 月 15 日 → 无需调整(8 ≥ 3)。
-
若为 2024 年 2 月 5 日 → 需调整为 2023 年 14 月 5 日。
-
-
拆分年份:
-
c = ⌊2024/100⌋ = 20
-
y = 2024 mod 100 = 24
-
-
代入公式:
#include <iostream> using namespace std;int zeller(int year, int month, int day) {if (month < 3) {month += 12;year -= 1;}int c = year / 100;int y = year % 100;int h = (day + 13*(month+1)/5 + y + y/4 + c/4 + 5*c) % 7;return h; // 0=星期六, 1=星期日, ..., 6=星期五 }int main() {int year = 2024, month = 8, day = 15;int week = zeller(year, month, day);const char* weeks[] = {"星期六", "星期日", "星期一", "星期二", "星期三", "星期四", "星期五"};cout << weeks[week]; // 输出:星期六return 0; }
注意事项
-
月份调整:必须将 1 月、2 月视为上一年的 13、14 月。
-
结果映射:公式中 h=0表示星期六,而非星期日。
-
适用范围:仅适用于格里高利历(公历,1582年10月15日之后)。