如何在Go中表示RFC-3339`-00:00`偏移量?
RFC-3339第4.3节()将如何在Go中表示RFC-3339`-00:00`偏移量?,go,time,Go,Time,RFC-3339第4.3节()将-00:00偏移定义为以下内容,这与Z或+00:00不同 4.3. Unknown Local Offset Convention If the time in UTC is known, but the offset to local time is unknown, this can be represented with an offset of "-00:00". This differs semantically from an o
-00:00
偏移定义为以下内容,这与Z
或+00:00
不同
4.3. Unknown Local Offset Convention
If the time in UTC is known, but the offset to local time is unknown,
this can be represented with an offset of "-00:00". This differs
semantically from an offset of "Z" or "+00:00", which imply that UTC
is the preferred reference point for the specified time. RFC2822
[IMAIL-UPDATE] describes a similar convention for email.
但是,我不确定如何在Go中表示这一点。当我用-00:00
解析一个时间并格式化它时,我得到一个Z
偏移量。例如:
- 输入:
2018-01-01T00:00:00-00:00
- 输出:
2018-01-01T00:00:00Z
Go不接受RFCs允许的所有时间格式 Go
time.time
类型使用整数,与浮点不同,整数没有正负零的概念。分析-00:00
和+00:00
偏移量的结果是相同的
比如说,
package main
import (
"fmt"
"time"
)
func main() {
var err error
var minus, plus time.Time
t := "2018-01-01T00:00:00-00:00"
minus, err = time.Parse(time.RFC3339, t)
if err != nil {
fmt.Println(err)
}
t = "2018-01-01T00:00:00+00:00"
plus, err = time.Parse(time.RFC3339, t)
if err != nil {
fmt.Println(err)
}
fmt.Println(minus, plus, minus.Equal(plus), minus == plus)
}
游乐场:
输出:
2018-01-01 00:00:00 +0000 UTC 2018-01-01 00:00:00 +0000 UTC true true
彼得索的回答是完美的。如果您需要根据偏移量未知的信息采取不同的行动,那么这可能会对您有所帮助 您可以构建自己的时间数据类型:
type MyTime struct {
// based on time.Time so we can do all normal time.Time stuff
time.Time
offsetUnknown bool
}
func ParseRFC3339(s string) (MyTime, error) {
time, err := time.Parse(time.RFC3339, s)
if err != nil {
return MyTime{}, err
}
return MyTime{
Time: time,
// maybe this condition needs improvement in case of false positives
offsetUnknown: strings.Contains(s, "-00:00"),
}, nil
}
根据offsetUnknown
需要以不同方式执行的任何函数,都可以在MyTime
结构上重写。这里有一个例子:
func (s MyTime) Format(layout string) string {
out := s.Time.Format(layout)
// again this is probably not the best solution
if layout == time.RFC3339 && s.offsetUnknown {
out = strings.Replace(out, "+00:00", "-00:00", -1)
}
return out
}
我不认为Go的
时间
包有一个未知偏移量的概念;这没有什么特别的用处。如果偏移量确实未知,则时间本身就有点无用,因为任何解释都可能不准确+/-12小时-足以使偶数日期可能偏离+/-1天。使用-00:00
时,时间是准确的,因为RFC表示“UTC时间已知”。只是偏移量未知,因此,例如,如果我们有一个时间2018-01-01T12:00:00-00:00
,我们知道确切的时间,但不知道偏移量,例如,时间是2018-01-01T11:00:00-01:00
还是2018-01-01T13:00:00+01:00
。在这种情况下,其区域设置是UTC。除了及时识别实例之外,时间没有义务提供任何信息。表示“在UTC中午,但我不知道它实际发生在什么地方”的时间是指与time.time
无关的“it”。关于“他们不接受RFCs允许的所有时间格式”,接受-00:00
偏移量,因为它解析时没有错误。但是,转换可能有损。@Grokify:time.Parse
不接受正零和负零偏移格式之间的区别。@Grokify:我建议您查看实际的偏移格式。解析负偏移量时,唯一要做的事情是反转计算出的正偏移量。正如这里所说的,一个整数-0等于+0,只要把它倒过来,它的信息就会丢失。我同意。“关于它的信息丢失了”就是为什么我说转换是有损的。
type MyTime struct {
// based on time.Time so we can do all normal time.Time stuff
time.Time
offsetUnknown bool
}
func ParseRFC3339(s string) (MyTime, error) {
time, err := time.Parse(time.RFC3339, s)
if err != nil {
return MyTime{}, err
}
return MyTime{
Time: time,
// maybe this condition needs improvement in case of false positives
offsetUnknown: strings.Contains(s, "-00:00"),
}, nil
}
func (s MyTime) Format(layout string) string {
out := s.Time.Format(layout)
// again this is probably not the best solution
if layout == time.RFC3339 && s.offsetUnknown {
out = strings.Replace(out, "+00:00", "-00:00", -1)
}
return out
}