上一主题 下一主题
ScriptCat,新一代的脚本管理器脚本站,与全世界分享你的用户脚本油猴脚本开发指南教程目录
返回列表 发新帖

Golang的时间格式化为什么是2006-01-02 15:04:05?

[复制链接]
  • TA的每日心情
    开心
    1 小时前
  • 签到天数: 116 天

    [LV.6]常住居民II

    25

    主题

    593

    帖子

    5699

    积分

    荣誉开发者

    精通各种语言的HelloWord!

    Rank: 10Rank: 10Rank: 10

    积分
    5699

    猫咪币纪念章活跃会员三好学生热心会员中秋纪念章国庆纪念章

    发表于 2021-12-29 17:31:20 | 显示全部楼层 | 阅读模式

    今天看了golang的时间和日期函数,发现了一个奇葩的问题,Golang的时间格式化的参考时间是2006-01-02 15:04:05

    官方文档给的说明是这样的(说了又好像没说):

    
        // The layout string used by the Parse function and Format method
        // shows by example how the reference time should be represented.
        // We stress that one must show how the reference time is formatted,
        // not a time of the user's choosing. Thus each layout string is a
        // representation of the time stamp,
        //  Jan 2 15:04:05 2006 MST
        // An easy way to remember this value is that it holds, when presented
        // in this order, the values (lined up with the elements above):
        //    1 2  3  4  5    6  -7
        // There are some wrinkles illustrated below.

    我就好奇为什么不用ymd来定义呢?在网上搜了一圈,发现大部分人都觉得很奇葩,不过Go语言中文网的polarisxu给出了如下解释,感觉还是蛮有趣的.


    02 为什么这么设计?

    为什么选择这个时间?不少人有这样的疑问。有人猜测是 Go 项目启动的时间等。但仔细研究,发现 Go Team 还是用心良苦,目的是解决大家记忆问题。

    比如常规的 ymd 格式,以 PHP 为例,一般这样 Y-m-d H:i:s,输出类似:2021-08-03 09:30:00,但如果我想输出:21-8-4 9:30:00,你不查手册,能写出来吗?你看看 PHP 文档中关于 date 格式化的说明,头有点大,竟然那么多,虽然常用的形式,大部分人都记得,但遇到不怎么常用的,就得查手册了。

    反观 Go 语言,它直接使用一个具体的时间来当做格式化字符串,需要什么格式,改这个时间格式即可。比如上面的例子,常规方式:2006-01-02 15:04:05,而 21-8-4 9:30:00 这种格式,只需要对应的改变值即可:06-1-2 3:04:05。而且,我查了下,PHP 没法表示没有前导零的分钟数和秒数,而 Go 很容易实现。很显然,Go 的方式是更合理、更易用的,对于各种变化,也能够更自如的应对。

    只不过,很多人对这个具体的时间觉得记不住。这一点,Go 官方也考虑到了。毕竟采用特殊的时间,目的就是为了解决大家记忆问题,因此要确保这个特殊时间也好记。Go 是这么设计的:

    1: month (January, Jan, 01, etc)2: day3: hour (15 is 3pm on a 24 hour clock)4: minute5: second6: year (2006)7: timezone (GMT-7 is MST)

    刚好是 1 2 3 4 5 6 7,据此进行变化即可。

    比如官方定义的常量:

    const ( ANSIC = "Mon Jan _2 15:04:05 2006" UnixDate = "Mon Jan _2 15:04:05 MST 2006" RubyDate = "Mon Jan 02 15:04:05 -0700 2006" RFC822 = "02 Jan 06 15:04 MST" RFC822Z = "02 Jan 06 15:04 -0700" // RFC822 with numeric zone RFC850 = "Monday, 02-Jan-06 15:04:05 MST" RFC1123 = "Mon, 02 Jan 2006 15:04:05 MST" RFC1123Z = "Mon, 02 Jan 2006 15:04:05 -0700" // RFC1123 with numeric zone RFC3339 = "2006-01-02T15:04:05Z07:00" RFC3339Nano = "2006-01-02T15:04:05.999999999Z07:00" Kitchen = "3:04PM")

    按 ANSIC 标准的日期格式,月、日、时、分、秒、年,最后加 MST 时区。对应就是 1 2 3 4 5 6 7。同时还可以随意加星期几。

    发现没有?围绕着 1 2 3 4 5 6 7 随意变化,真的不要太爽。我相信你用习惯了会发现 Go 这个设计真的太好了。

    03 总结

    Go 的设计原则之一:大道至简。尽量简介,让大家开心编程。我认为这个格式化时间的设计也体现了这一点,他们设计的很用心。

    知晓了为什么这么设计,我相信你看完这篇文章会从此爱上 Go 的时间格式化形式。

  • TA的每日心情
    慵懒
    2022-6-8 21:09
  • 签到天数: 48 天

    [LV.5]常住居民I

    135

    主题

    1798

    帖子

    1972

    积分

    管理员

    Rank: 10Rank: 10Rank: 10

    积分
    1972

    猫咪币纪念章热心会员活跃会员突出贡献三好学生中秋纪念章国庆纪念章

    发表于 2021-12-29 18:50:26 | 显示全部楼层
    记住12345
    上不慕古,下不肖俗。为疏为懒,不敢为狂。为拙为愚,不敢为恶。/ 微信公众号:一之哥哥
    回复

    使用道具 举报

    发表回复

    本版积分规则

    快速回复 返回顶部 返回列表