首页 > 解决方案 > 为什么日期在 1900 之前的时间包有不同的行为?

问题描述

我尝试使用golang的时间包从SQL服务器格式化一些带有时区的日期,但发现:

package main

import (
    "time"
    "fmt"
)

func main() {
    loc, _ := time.LoadLocation("Asia/Shanghai")
    endTime1 := time.Date(1, 1, 17, 23, 59, 59, 999*int(time.Millisecond), loc)
    fmt.Printf("format string 1 : %s\n", endTime1.UTC().Format("2006-01-02T15:04:05.000Z"))
    
    endTime2 := time.Date(2021, 1, 17, 23, 59, 59, 999*int(time.Millisecond), loc)
    fmt.Printf("format string 2 : %s\n", endTime2.UTC().Format("2006-01-02T15:04:05.000Z"))
}
# output
format string 1 : 0001-01-17T15:54:16.999Z
format string 2 : 2021-01-17T15:59:59.999Z

输出的“HH:mm:ss”部分不同。我终于找到了关键时间是1900-12-31,但从源代码或互联网上都没有找到关于那天的任何线索。

标签: gotime

解决方案


似乎与上海时区有关。

这个页面你可以阅读

1901 年 1 月 1 日 - 时区更改 (LMT → CST) 当当地标准时间即将到达 1901 年 1 月 1 日星期二 00:00:00 时,时钟被调回 0:05:43 小时至 1900 年 12 月 31 日星期一 23:改为当地标准时间 54:17。

此外,我们可以在go docs中找到更多信息

夏令时转换跳过或重复时间。例如,在美国,2011 年 3 月 13 日凌晨 2:15 从未发生过,而 2011 年 11 月 6 日凌晨 1:15 发生了两次。在这种情况下,时区的选择以及时间的选择都没有明确定义。Date 返回的时间在转换中涉及的两个区域之一中是正确的,但它不保证是哪个。


推荐阅读