go 中如何格式化时间

简介: go 中如何格式化时间

go 中如何格式化时间

前些天发现了一个巨牛的人工智能学习网站,通俗易懂,风趣幽默,忍不住分享一下给大家。点击跳转到网站

先来看一个简单的例子:

package main

import (
  "fmt"
  "time"
)

func main() {
  fmt.Println(time.Now().Format("2006"))
}

我们会觉得这会输出什么呢?输出的是 2022,也就是当前年份。

另一个例子:

package main

import 
  "fmt"
  "time"
)

func main() {
  fmt.Println(time.Now().Format("2006-01-02 15:04:05"))
}

输出:2022-08-04 09:43:56

如果之前写其他语言的,看到这个结果估计和我一样觉得百思不得其解,为什么不是 Y-m-d H:i:s 这种格式呢?而且那个参数看起来就是一个时间戳。

那个参数真的是时间戳吗?

答案我们可以点开 Format 的源码看看就知道了:

func (t Time) Format(layout string) string {
  // ... 省略,下面这个调用才是关键
  b = t.AppendFormat(b, layout)
  // ... 省略
}

我们看到 Format 里面具体处理逻辑在 AppendFormat 函数里面,再点开 AppendFormat 看看:

switch std & stdMask {
    case stdYear:
        y := year
        if y < 0 {
            y = -y
        }
        b = appendInt(b, y%100, 2)
    case stdLongYear:
        b = appendInt(b, year, 4)
    case stdMonth:
        b = append(b, month.String()[:3]...)
    case stdLongMonth:
        m := month.String()
        b = append(b, m...)
    // ... 省略其他 case
}

我们可以看到里面的 stdYearstdLongYear 之类的常量实际上就是我们传入到 Format 的参数里面的数字。

const (
  _                        = iota
  stdLongMonth             = iota + stdNeedDate  // "January"
  stdMonth                                       // "Jan"
  stdNumMonth                                    // "1"
  stdZeroMonth                                   // "01"
  stdLongWeekDay                                 // "Monday"
  stdWeekDay                                     // "Mon"
  stdDay                                         // "2"
  stdUnderDay                                    // "_2"
  stdZeroDay                                     // "02"
  stdUnderYearDay                                // "__2"
  stdZeroYearDay                                 // "002"
  stdHour                  = iota + stdNeedClock // "15"
  stdHour12                                      // "3"
  stdZeroHour12                                  // "03"
  stdMinute                                      // "4"
  stdZeroMinute                                  // "04"
  stdSecond                                      // "5"
  stdZeroSecond                                  // "05"
  stdLongYear              = iota + stdNeedDate  // "2006"
  stdYear                                        // "06"
  stdPM                    = iota + stdNeedClock // "PM"
  stdpm                                          // "pm"
  stdTZ                    = iota                // "MST"
  stdISO8601TZ                                   // "Z0700"  // prints Z for UTC
  stdISO8601SecondsTZ                            // "Z070000"
  stdISO8601ShortTZ                              // "Z07"
  stdISO8601ColonTZ                              // "Z07:00" // prints Z for UTC
  stdISO8601ColonSecondsTZ                       // "Z07:00:00"
  stdNumTZ                                       // "-0700"  // always numeric
  stdNumSecondsTz                                // "-070000"
  stdNumShortTZ                                  // "-07"    // always numeric
  stdNumColonTZ                                  // "-07:00" // always numeric
  stdNumColonSecondsTZ                           // "-07:00:00"
  stdFracSecond0                                 // ".0", ".00", ... , trailing zeros included
  stdFracSecond9                                 // ".9", ".99", ..., trailing zeros omitted

  stdNeedDate       = 1 << 8             // need month, day, year
  stdNeedClock      = 2 << 8             // need hour, minute, second
  stdArgShift       = 16                 // extra argument in high bits, above low stdArgShift
  stdSeparatorShift = 28                 // extra argument in high 4 bits for fractional second separators
  stdMask           = 1<<stdArgShift - 1 // mask out argument
)

所以,其实答案已经有了,我们对照一下我们的参数 2006-01-02 15:04:05,可以很简单在上述常量里面找到对应的常量:

  • 2006 => stdLongYear
  • 01 => stdZeroMonth
  • 02 => stdZeroDay
  • 15 => stdHour
  • 04 => stdZeroMinute
  • 05 => stdZeroSecond

layout 参数里面的 - 以及 : 都会原样输出。

根据给出的这些常量,我们就可以将时间格式化为我们想要的格式了。


目录
相关文章
|
5月前
|
Go
go fmt包格式化
go fmt包格式化
57 0
|
2月前
|
Go
Go - time.RFC3339 时间格式化
Go - time.RFC3339 时间格式化
47 7
|
3月前
|
存储 Go
go语言中fmt格式化包和内置函数汇总
【7月更文挑战第10天】本文介绍fmt包和`Errorf`用于创建格式化的错误消息。`fmt`包还涉及一些接口,如`Formatter`、`GoStringer`、`ScanState`、`Scanner`和`Stringer`,支持自定义格式化和输入/输出处理。
59 1
|
3月前
|
Go
go语言中格式化输出的占位符
【7月更文挑战第10天】`fmt` 包在 Go 语言中用于格式化输出,包括不同类型的占位符:%v(默认格式)、%+v(带字段名的结构体)、%#v(Go语法表示)、%T(类型表示)、%%(百分号)。布尔值用%t,整数有%b、%c、%d、%o、%q、%x、%X和%U。浮点数和复数用%b、%e、%E、%f、%g、%G。字符串和字节切片用%s、%q、%x、%X。指针用%p。占位符可配合+、-、#、空格和0进行调整。宽度和精度控制输出格式,例如 %.4g 控制小数精度。Go 没有 `%u`,但无符号整数默认打印为正数。运算符包括逻辑、比较、加减、乘除、移位、按位和按位异或等。
52 1
|
4月前
|
程序员 Go
【Go语言精进之路】Go语言fmt包深度探索:格式化输入输出的利器
【Go语言精进之路】Go语言fmt包深度探索:格式化输入输出的利器
94 3
|
5月前
|
自然语言处理 IDE Go
高效Go编程之格式化+代码注释+命名+分号+控制结构
【2月更文挑战第6天】高效Go编程之格式化+代码注释+命名+分号+控制结构
63 0
|
5月前
|
Unix Go
「有问必答」Go如何优雅的对时间进行格式化?
「有问必答」Go如何优雅的对时间进行格式化?
|
5月前
|
Go
Go 语言 Printf 函数和格式化动词详解
Printf() 函数可以使用多种格式化动词对输出进行格式化。下面是可以与所有数据类型一起使用的一些通用格式化动词: 以下动词适用于所有数据类型:
118 0
|
Go
go fmt包格式化
go fmt包格式化
58 0
Go 编程 | 连载 08 - 格式化输入输出
Go 编程 | 连载 08 - 格式化输入输出
Go 编程 | 连载 08 - 格式化输入输出