64 位有符号 unix 时间戳的溢出如何计算 12 月 4 日 292,277,026,596 的日期?
How was the date of December 4, 292,277,026,596 calculated for the overflow of the 64 bit signed unix timestamp?
我尝试使用最大的 64 位带符号整数自行计算日期,但结果总是与相差几百万年的另一个日期结束。我试过使用恒星年和闰年,但我总是得到至少几百万年之后的结果。
这是我迄今为止尝试过的方法:
dateA = 1970 + (9223372036854775807/31556926.08)
dateB = 1970 + (9223372036854775807/31536000) + (((9223372036854775807/31536000)/4)/365)
两个return都答错了。谁能指导我正确的方向?
您需要考虑闰年。满足以下条件的年份为闰年:
- 能被4整除;
- 除非能被100整除;
- 或如果能被400整除。
作为对年份的粗略估计,计算 1970 + 0x7fffffffffffffff // 86400 // (365 + 1/4 - 1/100 + 1/400)
得到的答案是 292277026596。我将推导确切的日期作为 reader.[=11= 的练习]
我在这个计算中使用了 Python 3,它给出了整数除法的真实结果。相应地调整 Python 2.
让我们使用 datetime
来完成一些繁重的工作。
>>> import datetime
首先,公历恰好每 400 年重复一次。这是 400 年周期中的天数:
>>> 365 * 400 + 100 - 4 + 1
146097
清楚了吗?每年至少有365天。会有 100 个闰年 (+100),除了能被 100 整除的年份不是闰年 (-4),除了能被 400 整除的年份是闰年 (+1)。
然后用它来算出有多少个 400 年的区块适合于等于最大 63 位整数的秒数:
>>> divmod((1 << 63) - 1, 146097 * 24 * 3600)
(730692561, 7161147007)
所以我们有 730692561 个 400 年的区块,还剩 7161147007 秒。 datetime
可以直接计算超出纪元的秒数:
>>> datetime.datetime(1970, 1, 1) + datetime.timedelta(seconds=7161147007)
datetime.datetime(2196, 12, 4, 15, 30, 7)
因此,除年份外,最后可表示的秒数是 12 月 4 日 15:30:07 UTC。
要获取年份,只需添加 730692561 个 400 年块:
>>> 2196 + 730692561 * 400
292277026596
我尝试使用最大的 64 位带符号整数自行计算日期,但结果总是与相差几百万年的另一个日期结束。我试过使用恒星年和闰年,但我总是得到至少几百万年之后的结果。
这是我迄今为止尝试过的方法:
dateA = 1970 + (9223372036854775807/31556926.08)
dateB = 1970 + (9223372036854775807/31536000) + (((9223372036854775807/31536000)/4)/365)
两个return都答错了。谁能指导我正确的方向?
您需要考虑闰年。满足以下条件的年份为闰年:
- 能被4整除;
- 除非能被100整除;
- 或如果能被400整除。
作为对年份的粗略估计,计算 1970 + 0x7fffffffffffffff // 86400 // (365 + 1/4 - 1/100 + 1/400)
得到的答案是 292277026596。我将推导确切的日期作为 reader.[=11= 的练习]
我在这个计算中使用了 Python 3,它给出了整数除法的真实结果。相应地调整 Python 2.
让我们使用 datetime
来完成一些繁重的工作。
>>> import datetime
首先,公历恰好每 400 年重复一次。这是 400 年周期中的天数:
>>> 365 * 400 + 100 - 4 + 1
146097
清楚了吗?每年至少有365天。会有 100 个闰年 (+100),除了能被 100 整除的年份不是闰年 (-4),除了能被 400 整除的年份是闰年 (+1)。
然后用它来算出有多少个 400 年的区块适合于等于最大 63 位整数的秒数:
>>> divmod((1 << 63) - 1, 146097 * 24 * 3600)
(730692561, 7161147007)
所以我们有 730692561 个 400 年的区块,还剩 7161147007 秒。 datetime
可以直接计算超出纪元的秒数:
>>> datetime.datetime(1970, 1, 1) + datetime.timedelta(seconds=7161147007)
datetime.datetime(2196, 12, 4, 15, 30, 7)
因此,除年份外,最后可表示的秒数是 12 月 4 日 15:30:07 UTC。
要获取年份,只需添加 730692561 个 400 年块:
>>> 2196 + 730692561 * 400
292277026596