time标准库
time标准库
时间在日常编程中使用非常多。time标准库中日历的计算采用的是公历
1. Time类型
-
Time代表一个纳秒精度的时间点。
-
程序中应使用Time类型值来保存和传递时间,而不能用指针。就是说,表示时间的变量和字段,应为time.Time类型,而不是*time.Time.类型。
-
一个Time类型值可以被多个goroutine同时使用。
-
时间点可以使用
Before
、After
和Equal
方法进行比较。 -
Sub
方法让两个时间点相减,生成一个Duration类型值(代表时间段)。 -
Add
方法给一个时间点加上一个时间段,生成一个新的Time类型时间点。 -
Time零值代表时间点January 1, year 1, 00:00:00.000000000 UTC。因为本时间点一般不会出现在使用中,
IsZero
方法提供了检验时间是否显式初始化的一个简单途径。 -
每一个时间都具有一个地点信息(及对应地点的时区信息),当计算时间的表示格式时,如
Format
、Hour
和Year
等方法,都会考虑该信息。 -
Local
、UTC
和In
方法返回一个指定时区(但指向同一时间点)的Time。修改地点/时区信息只是会改变其表示;不会修改被表示的时间点,因此也不会影响其计算。
func timeDemo() { now := time.Now() //获取当前时间 fmt.Printf("current time:%v\n", now) year := now.Year() //年 month := now.Month() //月 day := now.Day() //日 hour := now.Hour() //小时 minute := now.Minute() //分钟 second := now.Second() //秒 //02d输出的整数不足两位 用0补足 fmt.Printf("%d-%02d-%02d %02d:%02d:%02d\n", year, month, day, hour, minute, second) }
2. 时间戳
时间戳是自1970年1月1日0时0分0秒至当前时间的总毫秒数。它也被称为Unix时间戳(UnixTimestamp)。
这里指的是UTC时间,比北京时间晚8个小时。
func timestampDemo() { now := time.Now() //获取当前时间 timestamp1 := now.Unix() //时间戳 timestamp2 := now.UnixNano() //纳秒时间戳 fmt.Printf("current timestamp1:%v\n", timestamp1) fmt.Printf("current timestamp2:%v\n", timestamp2) }
3. Parse解析时间
func Parse(layout, value string) (Time, error)
解析一个格式化的时间字符串并返回它代表的时间,如果缺少表示时区的信息,Parse会将时区设置为UTC。
func ParseInLocation(layout, value string, loc *Location) (Time, error)
ParseInLocation类似Parse但有两个重要的不同之处。第一,当缺少时区信息时,Parse将时间解释为UTC时间,而ParseInLocation将返回值的Location设置为loc;第二,当时间字符串提供了时区偏移量信息时,Parse会尝试去匹配本地时区,而ParseInLocation会去匹配loc。
layout
的时间必须是"2006-01-02 15:04:05"
这个时间,当然格式不一定是这个,时间一定得是,这是go诞生的时间
func timeParse() { t, err := time.Parse("2006-01-02 15:04:05", "2022-07-28 18:06:00") if err != nil { panic(err) } fmt.Println(t) now := time.Now() fmt.Println(now) // 加载时区 loc, err := time.LoadLocation("Asia/Shanghai") if err != nil { fmt.Println(err) return } // 按照指定时区和指定格式解析字符串时间 timeObj, err := time.ParseInLocation("2006/01/02 15:04:05", now.Format("2006/01/02 15:04:05"), loc) if err != nil { fmt.Println(err) return } fmt.Println(timeObj) }
4. 格式化时间
func (t Time) Format(layout string) string
Format根据layout指定的格式返回t代表的时间点的格式化文本表示。
func timeFormat() { now := time.Now() // 格式化的模板为Go的出生时间2006年1月2号15点04分05秒 // 24小时制 fmt.Println(now.Format("2006-01-02 15:04:05.000")) // 12小时制 fmt.Println(now.Format("2006-01-02 03:04:05")) fmt.Println(now.Format("2006/01/02 15:04")) fmt.Println(now.Format("15:04 2006/01/02")) fmt.Println(now.Format("2006/01/02")) }
5. time.Unix()
func Unix(sec int64, nsec int64) Time
Unix创建一个本地时间,对应sec和nsec表示的Unix时间(从January 1, 1970 UTC至该时间的秒数和纳秒数)。
nsec的值在[0, 999999999]范围内是合法的。
func timestampDemo2(timestamp int64) { timeObj := time.Unix(timestamp, 0) //将时间戳转为时间格式 fmt.Println(timeObj) year := timeObj.Year() //年 month := timeObj.Month() //月 day := timeObj.Day() //日 hour := timeObj.Hour() //小时 minute := timeObj.Minute() //分钟 second := timeObj.Second() //秒 fmt.Printf("%d-%02d-%02d %02d:%02d:%02d\n", year, month, day, hour, minute, second) }
6. 时间间隔
time.Duration是time包定义的一个类型,它代表两个时间点之间经过的时间,以纳秒为单位。time.Duration表示一段时间间隔,可表示的最长时间段大约290年。
time包中定义的时间间隔类型的常量如下:
const ( Nanosecond Duration = 1 Microsecond = 1000 * Nanosecond Millisecond = 1000 * Microsecond Second = 1000 * Millisecond Minute = 60 * Second Hour = 60 * Minute )
例如:time.Duration表示1纳秒,time.Second表示1秒。
7. 时间计算
7.1 Add
func (t Time) Add(d Duration) Time
Add返回时间点t+d。
func main() { now := time.Now() later := now.Add(time.Hour) // 当前时间加1小时后的时间 fmt.Println(later) }
7.2 Sub
求两个时间之间的差值
func (t Time) Sub(u Time) Duration
返回一个时间段t-u。如果结果超出了Duration可以表示的最大值/最小值,将返回最大值/最小值。
要获取时间点t-d(d为Duration),可以使用t.Add(-d)。
func main() { now := time.Now() later := now.Add(time.Hour) // 当前时间加1小时后的时间 ret := later.Sub(now) fmt.Println(ret) }
7.3 Equal
func (t Time) Equal(u Time) bool
判断两个时间是否相同,会考虑时区的影响,因此不同时区标准的时间也可以正确比较。
本方法和用t==u不同,这种方法还会比较地点和时区信息。
7.4 Before
func (t Time) Before(u Time) bool
如果t代表的时间点在u之前,返回真;否则返回假。
7.5 After
func (t Time) After(u Time) bool
如果t代表的时间点在u之后,返回真;否则返回假。
8. 定时器
使用time.Tick(时间间隔)来设置定时器,定时器的本质上是一个通道(channel)
func tickDemo() { ticker := time.Tick(time.Second) //定义一个1秒间隔的定时器 for i := range ticker { fmt.Println(i)//每秒都会执行的任务 } }
time.AfterFunc(time.Second*10, func() { fmt.Println("10秒后执行") })
package main import ( "fmt" "sync" "time" ) /** *ticker只要定义完成,从此刻开始计时,不需要任何其他的操作,每隔固定时间都会触发。 *timer定时器,是到固定时间后会执行一次 *如果timer定时器要每隔间隔的时间执行,实现ticker的效果,使用 func (t *Timer) Reset(d Duration) bool */ func main() { var wg sync.WaitGroup wg.Add(2) //NewTimer 创建一个 Timer,它会在最少过去时间段 d 后到期,向其自身的 C 字段发送当时的时间 timer1 := time.NewTimer(2 * time.Second) //NewTicker 返回一个新的 Ticker,该 Ticker 包含一个通道字段,并会每隔时间段 d 就向该通道发送当时的时间。它会调 //整时间间隔或者丢弃 tick 信息以适应反应慢的接收者。如果d <= 0会触发panic。关闭该 Ticker 可 //以释放相关资源。 ticker1 := time.NewTicker(2 * time.Second) go func(t *time.Ticker) { defer wg.Done() for { <-t.C fmt.Println("get ticker1", time.Now().Format("2006-01-02 15:04:05")) } }(ticker1) go func(t *time.Timer) { defer wg.Done() for { <-t.C fmt.Println("get timer", time.Now().Format("2006-01-02 15:04:05")) //Reset 使 t 重新开始计时,(本方法返回后再)等待时间段 d 过去后到期。如果调用时t //还在等待中会返回真;如果 t已经到期或者被停止了会返回假。 t.Reset(2 * time.Second) } }(timer1) wg.Wait() }
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 微软正式发布.NET 10 Preview 1:开启下一代开发框架新篇章
· 没有源码,如何修改代码逻辑?
· PowerShell开发游戏 · 打蜜蜂
· 在鹅厂做java开发是什么体验
· WPF到Web的无缝过渡:英雄联盟客户端的OpenSilver迁移实战