在Golang中的夏令时小时数

huangapple go评论77阅读模式
英文:

Daylight saving hours in Golang

问题

我一直在设计一个用于调度界面的用户界面,用户可以在未来的几个小时内设置定时器。如果可能的话,我希望能够处理夏令时,我认为这应该很简单。在查看golang包中的time.Time时,我遇到了以下的不一致,如果这就是不一致的话。

package main

import (
   "fmt"
   "time"
)

func main(){
    const timeFormat = "2 Jan, 2006 3:04pm (MST)"
    test , err := time.Parse( timeFormat, "25 Oct, 2015 1:59am (BST)" )
    fmt.Println( test , test.UTC() , err)
    dur , _ := time.ParseDuration( "1m" )
    test = test.Add( dur )
    fmt.Println( test , test.UTC())

    fmt.Println( "--------------------" )

    test , err = time.Parse( timeFormat, "25 Oct, 2015 2:01am (BST)" )
    fmt.Println( test , test.UTC() , err)
    test = test.Add( dur )
    fmt.Println( test , test.UTC())

    test = test.Sub( dur )
    fmt.Println( test , test.UTC())
 }   

我知道2015年10月25日BST的凌晨2点应该会将时钟调回到格林尼治标准时间(UTC)的凌晨1点。如果我将BST的凌晨1点59分增加一分钟,时间确实会切换到GMT。

2015-10-25 01:59:00 +0100 BST 2015-10-25 00:59:00 +0000 UTC <nil>
2015-10-25 01:00:00 +0000 GMT 2015-10-25 01:00:00 +0000 UTC
--------------------
2015-10-25 02:01:00 +0000 BST 2015-10-25 02:01:00 +0000 UTC <nil>
2015-10-25 02:02:00 +0000 BST 2015-10-25 02:02:00 +0000 UTC

然而,如果我解析一个在BST的凌晨2点之后的时间,我期望它会像超过转换点的时间一样切换到GMT。为了确定过渡代码是否被Add例程调用,我再次增加了一分钟,但这也没有将时间恢复到GMT。

我本来期望以下情况之一发生:

a) BST始终保持为GMT+1

b) 对于BST为“无效”的任何时间,自动更改为正确的GMT时间(无效的BST是指从每年十月的最后一个星期日的凌晨2点到次年三月的最后一个星期日的凌晨2点之间的时间)

c) 如果在这些日期内使用BST创建日期,则抛出错误(也许还有其他国家的其他夏令时小时)。

否则,我将不得不检查用户是否输入了BST日期,是否超出了BST,并进行调整,或者强制用户使用UTC时间,这在某种程度上破坏了将夏令时功能内置到库中的目的。

在研究过程中,我注意到了这个视频https://www.youtube.com/watch?v=-5wpm-gesOY,并且已经决定这绝对不像我最初所认为的那么简单...

如果有任何见解或更好的处理夏令时的方法,我将不胜感激。

在Debian Wheezy上使用go版本1.0.2进行了编辑:重试使用go版本1.3.3并获得以下输出:

2015-10-25 01:59:00 +0100 BST 2015-10-25 00:59:00 +0000 UTC <nil>
2015-10-25 01:00:00 +0000 GMT 2015-10-25 01:00:00 +0000 UTC
--------------------
2015-10-25 01:00:00 +0000 GMT 2015-10-25 01:00:00 +0000 UTC <nil>
2015-10-25 01:01:00 +0000 GMT 2015-10-25 01:01:00 +0000 UTC

所以在后来的版本中似乎按照我预期的工作了...
还发现了这个问题https://stackoverflow.com/questions/2532729/daylight-saving-time-and-time-zone-best-practices?rq=1
所以我会仔细阅读它。

谢谢。

英文:

I have been designing a UI for a scheduling interface, where a user can set timers a number of hours into the future. I want to be able to handle daylight saving if possible, I thought it would be quite simple. Whilst checking out time.Time in the golang packages I ran into the following inconsistency, if that is what it is.

package main

import (
   &quot;fmt&quot;
   &quot;time&quot;
)

    func main(){
        const timeFormat = &quot;2 Jan, 2006 3:04pm (MST)&quot;
        test , err := time.Parse( timeFormat, &quot;25 Oct, 2015 1:59am (BST)&quot; )
        fmt.Println( test , test.UTC() , err)
        dur , _ := time.ParseDuration( &quot;1m&quot; )
        test = test.Add( dur )
        fmt.Println( test , test.UTC())
   
        fmt.Println( &quot;--------------------&quot;  )
   
        test , err = time.Parse( timeFormat, &quot;25 Oct, 2015 2:01am (BST)&quot; )
        fmt.Println( test , test.UTC() , err)
        test = test.Add( dur )
        fmt.Println( test , test.UTC())

        test = test.Sub( dur )
        fmt.Println( test , test.UTC())
     }   

I know that 2am on the 25 Oct 2015 in BST will should cause the clock to go back to 1am GMT (UTC). If I increment 1:59am BST by one minute the time does indeed switch to GMT.

2015-10-25 01:59:00 +0100 BST 2015-10-25 00:59:00 +0000 UTC &lt;nil&gt;
2015-10-25 01:00:00 +0000 GMT 2015-10-25 01:00:00 +0000 UTC
--------------------
2015-10-25 02:01:00 +0000 BST 2015-10-25 02:01:00 +0000 UTC &lt;nil&gt;
2015-10-25 02:02:00 +0000 BST 2015-10-25 02:02:00 +0000 UTC

However if I parse a time after 2am in BST I would expect it to switch to GMT just as incrementing the time over the transition would have. In case the transitional code was called by the Add routine I add a minute again but this also does not revert the time to GMT.

I would have expected one of the following to occur

a) for BST to always remain GMT+1

b) to any time where BST is "invalid" to automatically change to the correct GMT time (invalid BST is between 2am after the last Sunday in October and 2am after the last Sunday in March the following year)

c) an error to be thrown if a date is created within those dates with BST (and perhaps other daylight saving hours in other countries).

Otherwise I'll have to check if a user enters a date in BST whether that date lies outside BST and adjust or force users to UTC times, which kind of defeats the object of having daylight saving functions built into the library.

Whilst researching I spotted this https://www.youtube.com/watch?v=-5wpm-gesOY
and have decided it is definitely not as simple as I had at first assumed...

Any insight or a better way to handle daylight saving times would be appreciated.

Using go version 1.0.2 on Debian Wheezy

Edited: retried using go version 1.3.3
and got this output

2015-10-25 01:59:00 +0100 BST 2015-10-25 00:59:00 +0000 UTC &lt;nil&gt;
2015-10-25 01:00:00 +0000 GMT 2015-10-25 01:00:00 +0000 UTC
--------------------
2015-10-25 01:00:00 +0000 GMT 2015-10-25 01:00:00 +0000 UTC &lt;nil&gt;
2015-10-25 01:01:00 +0000 GMT 2015-10-25 01:01:00 +0000 UTC

So appears to work as I expected in later versions...
Have also found this question
https://stackoverflow.com/questions/2532729/daylight-saving-time-and-time-zone-best-practices?rq=1
So will be giving it a thorough read.

Thanks.

答案1

得分: 18

Go语言,和其他所有人一样,使用IANA时区数据库,该数据库定期更新,并包含在当前的Go发布版本中。

你使用的是go1.0.3版本,该版本发布于2012年3月(发布历史)。英国的时区数据是在之后添加的,用于2015年。

在进行时区计算时,始终使用最新版本的Go。

英文:

Go, like everybody else but Microsoft, uses the IANA Time Zone Database which has regular updates that are included in the current Go release.

You used go1.0.3 which was released in March 2012 (Release History). The British time zone data for 2015 was added later.

ALWAYS use a current version of Go for time zone calculations.

huangapple
  • 本文由 发表于 2015年3月17日 02:23:32
  • 转载请务必保留本文链接:https://go.coder-hub.com/29084228.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定