格式化

to string
格式化为字符串我们需要使用 time.Format 方法来转换成我们想要的格式

  1. fmt.Println(time.Now().Format("2006-01-02 15:04:05")) // 2021-11-11 15:32:09
  2. fmt.Println(time.Now().Format(time.UnixDate)) // Thu Nov 11 15:32:09 CST 2021

Format 函数中可以指定你想使用的格式,同时 time 包中也给了一些我们常用的格式

  1. const (
  2. ANSIC = "Mon Jan _2 15:04:05 2006"
  3. UnixDate = "Mon Jan _2 15:04:05 MST 2006"
  4. RubyDate = "Mon Jan 02 15:04:05 -0700 2006"
  5. RFC822 = "02 Jan 06 15:04 MST"
  6. RFC822Z = "02 Jan 06 15:04 -0700" // RFC822 with numeric zone
  7. RFC850 = "Monday, 02-Jan-06 15:04:05 MST"
  8. RFC1123 = "Mon, 02 Jan 2006 15:04:05 MST"
  9. RFC1123Z = "Mon, 02 Jan 2006 15:04:05 -0700" // RFC1123 with numeric zone
  10. RFC3339 = "2006-01-02T15:04:05Z07:00"
  11. RFC3339Nano = "2006-01-02T15:04:05.999999999Z07:00"
  12. Kitchen = "3:04PM"
  13. // Handy time stamps.
  14. Stamp = "Jan _2 15:04:05"
  15. StampMilli = "Jan _2 15:04:05.000"
  16. StampMicro = "Jan _2 15:04:05.000000"
  17. StampNano = "Jan _2 15:04:05.000000000"
  18. )

注意: galang 中指定的特定时间格式为 “2006-01-02 15:04:05 -0700 MST”

年、月、日、秒、毫秒、纳秒时间戳输出

  1. year := time.Now().Year() //年
  2. fmt.Println(year)
  3. month := time.Now().Month() //月
  4. fmt.Println(month)
  5. day := time.Now().Day() //日
  6. fmt.Println(day)
  7. hour := time.Now().Hour() //小时
  8. fmt.Println(hour)
  9. minute := time.Now().Minute() //分钟
  10. fmt.Println(minute)
  11. second := time.Now().Second() //秒
  12. fmt.Println(second)
  13. nanosecond := time.Now().Nanosecond() //纳秒
  14. fmt.Println(nanosecond)
  1. package main
  2. import (
  3. "time"
  4. "fmt"
  5. )
  6. func main() {
  7. fmt.Printf("时间戳(秒):%v;\n", time.Now().Unix())
  8. fmt.Printf("时间戳(毫秒):%v;\n",time.Now().UnixNano() / 1e6)
  9. fmt.Printf("时间戳(纳秒):%v;\n",time.Now().UnixNano())
  10. fmt.Printf("时间戳(纳秒转换为秒):%v;\n",time.Now().UnixNano() / 1e9)
  11. // 1e6 = 1*10^6 = 100000
  12. //时间戳(秒):1636616300;
  13. //时间戳(纳秒):1636616300046251000;
  14. //时间戳(毫秒):1636616300046;
  15. //时间戳(纳秒转换为秒):1636616300;
  16. }
  1. // 秒 1636616165
  2. fmt.Println(time.Now().Unix())
  3. // 获取指定日期的时间戳
  4. dt, _ := time.Parse("2006-01-02 15:04:05", "2021-11-11 15:32:09")
  5. // 1636644729
  6. fmt.Println(dt.Unix())
  7. // 1636702329
  8. fmt.Println(time.Date(2021, 11,12,15,32,9,0, time.Local).Unix())
  1. fmt.Println(time.Hour) // 1h0m0s 1小时
  2. fmt.Println(time.Second) // 1s 1秒
  3. fmt.Println(time.Now().Hour()) //16 下午4点
  4. // N天后的时间
  5. d := 3 * 24 * time.Hour
  6. afterNDay := time.Now().Add(d)
  7. fmt.Println("3天后的日期是", afterNDay.Format("2006-01-02"))

时间的计算�

01: 获取今天0点0时0分的时间戳

  1. currentTime := time.Now()
  2. startTime := time.Date(currentTime.Year(), currentTime.Month(), currentTime.Day(), 0, 0, 0, 0, currentTime.Location())
  3. fmt.Println(startTime)
  4. fmt.Println(startTime.Format("2006/01/02 15:04:05"))

02: 获取今天23:59:59秒的时间戳

  1. currentTime := time.Now()
  2. endTime := time.Date(currentTime.Year(), currentTime.Month(), currentTime.Day(), 23, 59, 59, 0, currentTime.Location())
  3. fmt.Println(endTime)
  4. fmt.Println(endTime.Format("2006/01/02 15:04:05"))

03: 获取1分钟之前的时间

  1. m, _ := time.ParseDuration("-1m")
  2. result := currentTime.Add(m)
  3. fmt.Println(result)
  4. fmt.Println(result.Format("2006/01/02 15:04:05"))

04: 获取1小时之前的时间

  1. m, _ := time.ParseDuration("-1h")
  2. result := currentTime.Add(m)
  3. fmt.Println(result)
  4. fmt.Println(result.Format("2006/01/02 15:04:05"))

05: 获取1分钟之后的时间

  1. m, _ := time.ParseDuration("1m")
  2. result := currentTime.Add(m)
  3. fmt.Println(result)
  4. fmt.Println(result.Format("2006/01/02 15:04:05"))

06: 获取1小时之后的时间

  1. m, _ := time.ParseDuration("1h")
  2. result := currentTime.Add(m)
  3. fmt.Println(result)
  4. fmt.Println(result.Format("2006/01/02 15:04:05"))

07 :计算两个时间戳

  1. afterTime, _ := time.ParseDuration("1h")
  2. result := currentTime.Add(afterTime)
  3. beforeTime, _ := time.ParseDuration("-1h")
  4. result2 := currentTime.Add(beforeTime)
  5. m := result.Sub(result2)
  6. fmt.Printf("%v 分钟 \n", m.Minutes())
  7. h := result.Sub(result2)
  8. fmt.Printf("%v小时 \n", h.Hours())
  9. d := result.Sub(result2)
  10. fmt.Printf("%v 天\n", d.Hours()/24)

08: 判断一个时间是否在一个时间之后

  1. stringTime, _ := time.Parse("2006-01-02 15:04:05", "2019-12-12 12:00:00")
  2. beforeOrAfter := stringTime.After(time.Now())
  3. if true == beforeOrAfter {
  4. fmt.Println("2019-12-12 12:00:00在当前时间之后!")
  5. } else {
  6. fmt.Println("2019-12-12 12:00:00在当前时间之前!")
  7. }

09: 判断一个时间相比另外一个时间过去了多久

  1. startTime := time.Now()
  2. time.Sleep(time.Second * 5)
  3. fmt.Println("离现在过去了:", time.Since(startTime))

其他

摘自:知乎 go 学堂 https://zhuanlan.zhihu.com/p/343014745

再来看Time结构体在源文件中的定义:

  1. type Time struct {
  2. wall uint64
  3. ext int64
  4. loc *Location
  5. }

获取时间相关操作

1、获取当前时间戳
函数原型:func (t Time) Unix() int64
示例代码:

  1. seconds := time.Now().Unix()

2、获取当前年月日时分秒和星期几(数字不带前导0)
函数原型:

  1. func (t Time) Date() (yearint, month Month, dayint)
  2. func(t Time)Clock() (hour, min, secint)
  3. func(t Time)Hour()int
  4. func(t Time)Minute()int
  5. func(t Time)Second()int

示例代码:

  1. //获取当前时间的Time结构体实例
  2. t := time.Now()
  3. //通过Date函数同时获取年月日
  4. year, month, day := t.Date()
  5. //假设日期为2021-1-7 打印结果为 year:2021, month:1, day:7
  6. fmt.Printf("year:%d, month:%d, day:%d\n", year, month, day)
  7. //通过Clock函数同时获取时分秒
  8. hour, minute, second := t.Clock()
  9. //假设时间是18:51:9 打印结果 hour:18,minute:51,second:9
  10. fmt.Printf("hour:%d,minute:%d,second:%d\n", hour, minute, second)
  11. //也可以单独获取年、月、日、时、分、秒、星期几
  12. year := t.Year() //获取所属年份
  13. month := t.Month() //获取所属月份,不带前导零
  14. day := t.Day() //获取所属日,不带前导零
  15. hour := t.Hour() //获取当前小时
  16. minutes := t.Minute() //获取当前分钟
  17. seconds := t.Seconds() //获取当前描述
  18. nanosecond := t.Nanosecond() //获取当前纳秒数

3、获取今天是星期几
函数原型:func (t Time) Weekday() Weekday
该函数返回值类型是Weekday,即可以表示成数字星期几,也可以输出成星期的英文表示。示例代码:

  1. //获取当前时间的Time结构体实例
  2. t := time.Now()
  3. //获取是星期几, t.Weekday返回的是Weekday类型
  4. //Weekday类型在源码的定义是 type Weekday int
  5. weekday := t.Weekday()
  6. // 打印出星期几的数字表示和英文表示
  7. // 假设是星期四,打印结果:weekday=4, weekday(string)=Thursday
  8. fmt.Printf("weekday=%d, weekday(string)=%s\n\n", weekday, weekday)

4、返回当前时间是一年中的第几天
函数原型:func (t Time) YearDay() int
示例代码:

  1. //获取当前时间的Time结构体实例
  2. t := time.Now()
  3. yearday := time.Now().YearDay()
  4. // 假设时间是2021-01-07日 打印结果 yearday = 7
  5. fmt.Printf("yearday=%d\n\n", yearday)

时间戳和日期字符串之间的转换

1、时间戳格式化成日期字符串
函数原型:

  1. func Unix(sec int64, nsec int64) Time
  2. func (t Time) Format(layout string) string

该转换主要分三步:

  1. 将时间戳类型转成int64类型
  2. 将int64类型时间戳转换成Time结构
  3. 调用Time结构体的Format函数

示例代码:

  1. // 1、将时间戳转换成int64类型
  2. timestamps := int64(1609945385) //该时间戳代表2021-01-06 23:03:05
  3. //2、将int64类型时间戳转换成Time结构,time.Unix函数的第2个参数代表纳秒数
  4. t := time.Unix(timestamps, 0)
  5. //3、调用Time结构体的Format函数,这里我们定义一组格式
  6. var formats = []string{
  7. "2006年01月02日 15时04分05秒",
  8. "2006-01-02 15:04:05",
  9. "2006/01/02 15:04:05",
  10. "06-01-02",
  11. "06年01月02日",
  12. "2006.01.02",
  13. "06/1/2",
  14. }
  15. for _, layout := range formats {
  16. result := t.Format(layout)
  17. fmt.Printf("日期格式:%s, 转换结果:%s \n", layout, result)
  18. }

2、日期字符串按格式转换成时间戳函数原型:funcParseInLocation(layout, valuestring, loc *Location) (Time,error)
该转换主要分三步:

  1. 调用time.LoadLocation函数,设置特定的时区。否则,在第2步,默认会按UTC时区解析时间。
  2. 调用time.ParseInLocation函数,将字符串转换成Time结构体
  3. 调用Time结构体的Unix函数转换成对应的时间戳

示例代码:

  1. // 该结构体代表将value按format格式解析成Time结构体实例
  2. type ParseFormat struct {
  3. format string // 日期格式
  4. value string // 要转换的日期
  5. }
  6. //这里定义一组时间格式和要转换的日期字符串
  7. var parseFormats = []ParseFormat{
  8. {"2006年01月02日 15时04分05秒", "2021年01月06日 23时03分05秒"},
  9. {"2006-01-02 15:04:05", "2021-01-06 23:03:05"},
  10. {"2006/01/02 15:04:05", "2021/01/06 23:03:05"},
  11. {"06-01-02", "21-01-06"},
  12. {"06年01月02日", "21年01月06日"},
  13. {"2006.01.02", "2021.01.06"},
  14. {"06/1/2", "21/1/6"},
  15. }
  16. //1、设置时区为上海,即北京时间
  17. loc, _ := time.LoadLocation("Asia/Shanghai")
  18. for _, parseFormat := range parseFormats {
  19. // 2、将日期字符串按特定格式转换成特定时区下的Time结构体
  20. t, _ := time.ParseInLocation(parseFormat.format, parseFormat.value, loc)
  21. // 3、调用Time结构体的Unix函数转换成对应的时间戳
  22. unix := t.Unix()
  23. fmt.Printf("时区:%v, 时间戳(秒):%d\n", t.Location(), unix)
  24. }

时间之间的常用计算操作

这里介绍一个新的数据类型Duration。在time源码包中的定义如下:

  1. type Duration int64

Duration,代表的是两个时间点之间的持续时间(纳秒数),即时段。
上文的Time结构体类型,代表的是时刻,即一个时间点。如下图:
image.png
Duration = t1 - t2 单位:纳秒

1、计算两个日期之间相差多少秒该转换主要分三步:

  • 调用time.LoadLocation函数,设置特定的时区。否则,第2步默认会按UTC时区解析时间。
  • 调用time.ParseInLocation函数,将字符串转换成Time结构体
  • 调用Time结构体的计算函数Sub,得到两个时间之间的Duration

示例代码:

  1. t1str := "2021-01-07 15:57:23"
  2. t2str := "2021-01-07 18:57:23"
  3. layout := "2006-01-02 15:04:05" //时间字符串的格式
  4. //1、将时间字符串转换成Time类型
  5. location, _ := time.LoadLocation("Asia/Shanghai")
  6. t1 := time.ParseInLocation(layout, t1str, location)
  7. t2 := time.ParseInLocation(layout, t2str, location)
  8. //2、计算两个Time结构实例之间的差
  9. d := t2.Sub(t1)
  10. //3、根据返回的Duration类型的d转换成相应的小时/分钟/秒数
  11. hours := d.Hours() //转换成两个时刻相差的小时数
  12. minutes := d.Minutes() //转换成两个时刻相差的分钟数
  13. seconds := d.Seconds() //转换成两个时刻相差的秒数
  14. milliseconds := d.Milliseconds() //转换成两个时刻相差的毫秒数
  15. microseconds := d.Microseconds() //转换成两个时刻相差的微妙数
  16. nanoseconds := d.Nanoseconds() //转换成两个时刻相差的纳秒数

2、获取从某个时间 至今 经过的时间Duration函数原型:funcSince(t Time) Duration
场景:假设你和你女朋友相识于2014-10-02 13:14:15,计算出至今你们总共认识了多长时间。示例代码:

  1. t1str := "2014-10-02 13:14:15"
  2. layout := "2006-01-02 15:04:05" //时间字符串的格式
  3. //1、将时间字符串转换成Time类型
  4. location, _ := time.LoadLocation("Asia/Shanghai")
  5. t := time.ParseInLocation(layout, t1str, location)
  6. //2、计算两个Time结构实例之间的差
  7. d := time.Since(t)
  8. //2、根据返回的d转换成响应的小时/分钟/秒数
  9. hours := d.Hours() //转换成两个时刻相差的小时数
  10. minutes := d.Minutes() //转换成两个时刻相差的分钟数
  11. seconds := d.Seconds() //转换成两个时刻相差的秒数
  12. milliseconds := d.Milliseconds() //转换成两个时刻相差的毫秒数
  13. microseconds := d.Microseconds() //转换成两个时刻相差的微妙数
  14. nanoseconds := d.Nanoseconds() //转换成两个时刻相差的纳秒数
  15. fmt.Printf("从%s至今你们一起度过了共%d", t1str, d.Round(24*time.Hour))
  16. fmt.Printf("从%s至今共一起度过了%f小时\n", t1str, time.Now().Format(layout), hours)

3、计算从今天到未来某个时间经过的时间 函数原型:funcUntil(t Time) Duration
示例代码:

  1. t1str := "2021-12-21 13:14:15"
  2. layout := "2006-01-02 15:04:05" //时间字符串的格式
  3. //第1步,将时间字符串转换成Time类型
  4. location, _ := time.LoadLocation("Asia/Shanghai")
  5. t := time.ParseInLocation(layout, t1str, location)
  6. //第2步,计算两个Time结构实例之间的差
  7. d := time.Until(t)
  8. //第3步,根据返回的d转换成响应的小时/分钟/秒数
  9. hours := d.Hours() //转换成两个时刻相差的小时数
  10. fmt.Printf("距女朋友生日%s还有%f小时\n", t1str, hours)

4、时间之间的比较:是早、是晚、还是相等相关函数:
func (t Time) After(u Time) bool
func (t Time) Before(u Time) bool
func (t Time) Equal(u Time) bool
场景:你和女朋友约会,约好2021-12-12 13:14:15 在餐厅门口见。这时,你看了看手表,在大脑中和约定时间快速的比较了下,判断是来早了还是来晚了

  1. pivot := "2021-12-12 13:14:15"
  2. layout := "2006-01-02 15:04:05" //时间字符串的格式
  3. //第1步,将时间字符串转换成Time类型
  4. location, _ := time.LoadLocation("Asia/Shanghai")
  5. pivotT := time.ParseInLocation(layout, t1str, location)
  6. //第2步,获取现在的时间
  7. t := time.Now()
  8. //第3步,和约定时间比较下是否来早了
  9. if t.Before(pivotT) {
  10. fmt.Println("来早了")
  11. }
  12. //和约定时间比较一下,看是否来晚了
  13. if t.After(pivotT) {
  14. fmt.Println("oh,糟糕,来晚了")
  15. }
  16. //和约定时间比较一下,一看,刚刚好
  17. if t.Equal(pivotT) {
  18. fmt.Println("还好,还好,刚刚好")
  19. }

参考: