go - time包的定时器/断续器
from: https://www.kancloud.cn/digest/batu-go/153534
定时器
在time包中有两个函数可以帮助我们初始化time.Timer
time.Newtimer函数
初始化一个到期时间据此时的间隔为3小时30分的定时器
t := time.Newtimer(3*time.Hour + 30*time.Minute)
注意,这里的变量t是*time.NewTimer类型的,这个指针类型的方法集合包含两个方法
- Rest
用于重置定时器。该方法返回一个bool类型的值 - Stop
用来停止定时器。该方法返回一个bool类型的值,如果返回false,说明该定时器在之前已经到期或者已经被停止了,反之返回true。
通过定时器的字段C,我们可以及时得知定时器到期的这个事件来临,C是一个chan time.Time类型的缓冲通道,一旦触及到期时间,定时器就会向自己的C字段发送一个time.Time类型的元素值
示例一:一个简单定时器
package mainimport ("fmt""time"
)func main(){//初始化定时器t := time.NewTimer(2 * time.Second)//当前时间now := time.Now()fmt.Printf("Now time : %v.\n", now)expire := <- t.Cfmt.Printf("Expiration time: %v.\n", expire)
}
Now time : 2015-10-31 01:19:07.210771347 +0800 CST.
Expiration time: 2015-10-31 01:19:09.215489592 +0800 CST.
示例二:我们在改造下之前的那个简单超时操作
package mainimport ("fmt""time"
)
func main(){//初始化通道ch11 := make(chan int, 1000)sign := make(chan byte, 1)//给ch11通道写入数据for i := 0; i < 1000; i++ {ch11 <- i}//单独起一个Goroutine执行selectgo func(){var e intok := true//首先声明一个*time.Timer类型的值,然后在相关case之后声明的匿名函数中尽可能的复用它var timer *time.Timerfor{select {case e = <- ch11:fmt.Printf("ch11 -> %d\n",e)case <- func() <-chan time.Time {if timer == nil{//初始化到期时间据此间隔1ms的定时器timer = time.NewTimer(time.Millisecond)}else {//复用,通过Reset方法重置定时器timer.Reset(time.Millisecond)}//得知定时器到期事件来临时,返回结果return timer.C}():fmt.Println("Timeout.")ok = falsebreak}//终止for循环if !ok {sign <- 0break}}}()//惯用手法,读取sign通道数据,为了等待select的Goroutine执行。<- sign
}
time.After函数
time.After函数, 表示多少时间之后,但是在取出channel内容之前不阻塞,后续程序可以继续执行。鉴于After特性,其通常用来处理程序超时问题。
package mainimport ("fmt""time"
)func main(){ch1 := make(chan int, 1)ch2 := make(chan int, 1)select {case e1 := <-ch1://如果ch1通道成功读取数据,则执行该case处理语句fmt.Printf("1th case is selected. e1=%v",e1)case e2 := <-ch2://如果ch2通道成功读取数据,则执行该case处理语句fmt.Printf("2th case is selected. e2=%v",e2)case <- time.After(2 * time.Second):fmt.Println("Timed out")}
}
Timed out
- time.Sleep函数,表示休眠多少时间,休眠时处于阻塞状态,后续程序无法执行.
time.Afterfunc函数
示例三:自定义定时器
package mainimport ("fmt""time"
)
func main(){var t *time.Timerf := func(){fmt.Printf("Expiration time : %v.\n", time.Now())fmt.Printf("C`s len: %d\n", len(t.C))}t = time.AfterFunc(1*time.Second, f)//让当前Goroutine 睡眠2s,确保大于内容的完整//这样做原因是,time.AfterFunc的调用不会被阻塞。它会以一部的方式在到期事件来临执行我们自定义函数f。time.Sleep(2 * time.Second)
}
Expiration time : 2015-10-31 01:04:42.579988801 +0800 CST.
C`s len: 0
第二行打印内容说明:定时器的字段C并没有缓冲任何元素值。这也说明了,在给定了自定义函数后,默认的处理方法(向C发送代表绝对到期时间的元素值)就不会被执行了。
断续器
结构体类型time.Ticker表示了断续器的静态结构。
就是周期性的传达到期时间的装置。这种装置的行为方式与仅有秒针的钟表有些类似,只不过间隔时间可以不是1s。
初始化一个断续器
var ticker *timeTicker = time.NewTicker(time.Second)
示例一:使用时间控制停止ticke
package mainimport ("fmt""time"
)func main(){ //初始化断续器,间隔2svar ticker *time.Ticker = time.NewTicker(1 * time.Second)go func() {for t := range ticker.C {fmt.Println("Tick at", t)}}()time.Sleep(time.Second * 5) //阻塞,则执行次数为sleep的休眠时间/ticker的时间ticker.Stop() fmt.Println("Ticker stopped")
}
Tick at 2015-10-31 01:29:34.41859284 +0800 CST
Tick at 2015-10-31 01:29:35.420131668 +0800 CST
Tick at 2015-10-31 01:29:36.420565647 +0800 CST
Tick at 2015-10-31 01:29:37.421038416 +0800 CST
Tick at 2015-10-31 01:29:38.41944582 +0800 CST
Ticker stopped
示例二:使用channel控制停止ticker
package mainimport ("fmt""time"
)func main(){ //初始化断续器,间隔2svar ticker *time.Ticker = time.NewTicker(100 * time.Millisecond) //num为指定的执行次数num := 2c := make(chan int, num) go func() {for t := range ticker.C {c <- 1fmt.Println("Tick at", t)}}()time.Sleep(time.Millisecond * 1500)ticker.Stop() fmt.Println("Ticker stopped")
}
go - time包的定时器/断续器相关推荐
- go time包定时器和断续器
定时器 在time包中有两个函数可以帮助我们初始化time.Timer time.Newtimer函数 初始化一个到期时间据此时的间隔为3小时30分的定时器 t := time.Newtimer(3* ...
- Go 定时器和断续器
1.定时器 Go语言中定时器可以实现在指定时间点执行特定的事件,定时器的实质是单向通道,time.Timer结构体类型中有一个time.Time类型的单向chan,具体声明如下: type Timer ...
- Golang停止ticker断续器
1.原代码如下 package mainimport ("fmt""time" )func main() {intchan := make(chan int,1 ...
- golang并发编程-04-通道-02-定时器、断续器
文章目录 1. 定时器 1.1 time.NewTimer 1.2 <-time.After() 1.3 停止 1.4 定时器重置 2 断续器 2.1 断续器使用 2.2 断续器中断 1. 定时 ...
- 介绍 Go 断续器(Tickers)
介绍 Go 断续器(Tickers) 本文我们介绍 Go 断续器(Tickers)以及如何在应用中有效使用断续器.当我们需要在特定时间间隔内周期性重复执行动作,我们可以使用断续器.与协程一起使用可以实 ...
- 中国真空断续器市场现状研究分析与发展前景预测报告(2022)
[报告篇幅]:109 [报告图表数]:150 [报告出版时间]:2021年12月 报告摘要 2021年中国真空断续器市场销售收入达到了 万元,预计2028年可以达到 万元,2022-2028期间年复合 ...
- PackageManagerService启动详解(五)之Android包信息体和解析器(中)
PKMS启动详解(五)之Android包信息体和包解析器(中) Android PackageManagerService系列博客目录: PKMS启动详解系列博客概要 PKMS启动详解(一)之 ...
- (一)串口通信:同步通信与异步通信的区别;异步通信:握手、收发过程、心跳包、定时器、粘包、拆包、丢包、误包(或误码)、帧结构、奇偶校验、CRC校验等等
目录 第一章.简介 第二章.并行通信 第三章.串行通信 3.1.同步通信 3.1.1.同步通信的原理 3.1.2.同步通信的数据格式 3.1.3.同步通信特点 3.2.异步通信 3.2.1.异步通信的 ...
- JavaScript的定时器延时器
定时器 定义 按照设定的时间间隔 循环往复执行程序也就是 按照设定的时间间隔 每间隔设定的时间 执行一次程序事件间隔的单位是 毫秒也就是 按照间隔时间 一直重复执行程序 语法 setInterval( ...
最新文章
- MFC 加载并显示图片的四种方法
- oracle ebs form视频,ORACLE EBS FORM利用模板开发步骤
- 进入Windows的世界
- PAT A 1118. Birds in Forest (25)【并查集】
- 使用各类BeanUtils的时候,切记注意这个坑!
- Layui layer详细参数解释说明
- java中date类型如何赋值_Java 中的类型传递问题解惑
- 新东方预计6个月亏损超8亿美元
- 安卓拍照上传php服务器,Android拍照上传至PHP服务器并写入MySql数据库(下)
- mysql创建数据库sql语句_创建数据库的SQL语句:mysql数据库
- 尤大大(尤雨溪)的年度总结、预期
- PHPstrom + xdebug + postman断点调试代码 php谷歌浏览器代码断点调试
- 【ppt入门教程】Win7系统怎样实现ppt双屏显示不同的内容
- PS | 工作区,工具栏不见了怎么办 -- 复位基本功能
- Web 安全工具篇:Burp Suite 使用指南
- 2019清华计算机考研名单,2019年清华大学硕士研究生拟录取名单公示(清华MBA,考生编号排序)...
- 2018.1.28 牛客网2018年全国多校算法寒假训练营练习比赛题解
- 哪些数字适合作为域名主体?
- Linux系统安装中文字体
- 国内服务器证书,中国互联网协会-CNNIC推出国内首个服务器域名证书