Go 如何关闭计时器频道?
我有一个计时器,它会被某些事件重置。go函数使用范围监听频道。如何关闭通道,以便循环退出Go 如何关闭计时器频道?,go,Go,我有一个计时器,它会被某些事件重置。go函数使用范围监听频道。如何关闭通道,以便循环退出 func resetTimer(){ if rf.electionTimer != nil { rf.electionTimer.Stop() } } rf.electionTimer = time.NewTimer(electionTime) for _ = range rf.electionTimer.C { // Do someth
func resetTimer(){
if rf.electionTimer != nil {
rf.electionTimer.Stop()
}
}
rf.electionTimer = time.NewTimer(electionTime)
for _ = range rf.electionTimer.C {
// Do something
}
使用一个通道来发出环路应该退出的信号
rf.done := make(chan struct{})
rf.electionTimer = time.NewTimer(electionTime)
func stopTimer(){
if rf.electionTimer != nil {
rf.electionTimer.Stop()
close(rf.done)
}
}
选择环路中的信号通道和定时器通道。当信号通道关闭时,环路中断
loop:
for {
select {
case t := <-rf.electionTimer.C:
// Do something
case <-rf.done:
break loop
}
}
循环:
为了{
挑选{
案例t:=来自的通道不会多次输出时间。它只会在计时器结束后输出一次时间。因此,在for
循环中使用rf.electionTimer
是无用的
尝试将for
循环替换为:
t := <-rf.electionTimer.C
// Do something with t
time.Timer只会触发一次,因此实际上不需要在它上面设置范围。你是想使用time.Ticker吗?@ardent过期的计时器可以重置,这意味着它实际上可以触发多次(与Ticker不同,如果控制代码需要,它可以不定期地触发)正如霍布斯所提到的,我使用了随机间隔和定时器重置。用一个简单的bool
而不是chan结构{}来代替rf.done可能会更有效率和意义
@acid,当从另一个goroutine调用Stop和Reset时引入数据竞争。谢谢,Cerise Limon。我正在重置计时器。我尝试了与您编写的类似的方法,但我使用了bool类型的通道,它在我尝试rf时阻塞了通道。完成@2ank3th发送到通道可以工作,但我无法确定为什么不工作为您工作时不会看到更多代码。我最初的解决方案是使用t:=
rf.electionTimer.Reset(0)