golang中timer定时器实现原理

一般我们导入import ("time")包,然后调用time.NewTicker(1 * time.Second) 实现一个定时器:

func timer1() {
	timer1 := time.NewTicker(1 * time.Second)
	for {
		select {
		case <-timer1.C:
			xxx() //执行我们想要的操作
		}
	}
}

再看看timer包中NewTicker的具体实现:

func NewTicker(d Duration) *Ticker {
	if d <= 0 {
		panic(errors.New("non-positive interval for NewTicker"))
	}
	// Give the channel a 1-element time buffer.
	// If the client falls behind while reading, we drop ticks
	// on the floor until the client catches up.
	c := make(chan Time, 1)
	t := &Ticker{
		C: c,
		r: runtimeTimer{
			when:   when(d),
			period: int64(d),
			f:      sendTime,
			arg:    c,
		},
	}
	startTimer(&t.r)
	return t
}

其中Ticker的具体struct如下:

type Ticker struct {
	C <-chan Time // The channel on which the ticks are delivered.
	r runtimeTimer
}

Ticker中的C为数据类型为Time的单向管道,只能读,不能写

再分下一下runtimeTimer的参数:

r: runtimeTimer{
			when:   when(d),
			period: int64(d),
			f:      sendTime,
			arg:    c,
		}

其中sendTime为回调函数,startTimer时候注册的,arg为回调函数需要的参数arg

startTimer(&t.r)

再进一步看看startTimer的实现:

func sendTime(c interface{}, seq uintptr) {
	// Non-blocking send of time on c.
	// Used in NewTimer, it cannot block anyway (buffer).
	// Used in NewTicker, dropping sends on the floor is
	// the desired behavior when the reader gets behind,
	// because the sends are periodic.
	select {
	case c.(chan Time) <- Now():
	default:
	}
}

通过往管道里面写时间,注意我们Ticker结构里面的C是单向管道,只能读不能写,那要怎么写数据了

通过类型转化,因为channel是一个原生类型,因此不仅支持被传递,还支持类型转换,装换成双向的管道channel,往里面

写数据,用户API那边提供的是单向管道,用户只能就只能读数据,就相当于一层限制

最后,调用执行具体xxx函数,实现定时执行某些事件的功能:

for {
    select {
	case <-timer1.C:
	  xxxx()
     }
   }
时间: 2025-01-17 11:52:50

golang中timer定时器实现原理的相关文章

关于C#中Timer定时器的重入问题解决方法

项目中用到了定时器随着服务启动作定时任务,按指定的准点时间定时执行相关操作,但是在指定准点时间内我只想让它执行一次,要避免重入问题的发生. 首先简单介绍一下timer,这里所说的timer是指的System.Timers.timer,顾名思义,就是可以在指定的间隔是引发事件.官方介绍在这里,摘抄如下: Timer 组件是基于服务器的计时器,它使您能够指定在应用程序中引发 Elapsed 事件的周期性间隔.然后可通过处理这个事件来提供常规处理. 例如,假设您有一台关键性服务器,必须每周 7 天.每

C#中Timer定时器的使用示例

关于C#中timer类 在C#里关于定时器类就有3个: 1.定义在System.Windows.Forms里 2.定义在System.Threading.Timer类里 3.定义在System.Timers.Timer类里 System.Windows.Forms.Timer是应用于WinForm中的,它是通过Windows消息机制实现的,类似于VB或Delphi中的Timer控件,内部使用API SetTimer实现的.它的主要缺点是计时不精确,而且必须有消息循环,Console Applic

asp.net中Timer定时器在web中无刷新的使用

最近在做一个项目的时候,web端的数据需要与数据源进行实时同步,并保证数据的准确性,当时,考虑到使用ajax异步刷新技术.但后来在网上查找相关资料时,发现这样做,太浪费资源了,因为ajax的提交请求不应该这么频繁的,只适用于那种手动请求响应的那种,因此这种办法是行不通了,后来,发现asp.net中有一个定时器Timer,可以进行实时同步数据,因此本人就做了一个小小的测试,发现还挺好用的,于是乎就有了下文.如下: aspx页面中的代码: <form id="form1" runat

golang 中的定时器(timer),更巧妙的处理timeout

今天看到kite项目中的一段代码,发现挺有意思的. // generateToken returns a JWT token string. Please see the URL for details: // http://tools.ietf.org/html/draft-ietf-oauth-json-web-token-13#section-4.1 func generateToken(aud, username, issuer, privateKey string) (string,

golang的Timer定时器

// code_047_Timer project main.go package main import ( "fmt" "time" ) func main() { timer1 := time.NewTimer(time.Second * 2) t1 := time.Now() fmt.Printf("t1:%v\n", t1) t2 := <-timer1.C fmt.Printf("t2:%v\n", t2)

golang 中timer,ticker 的使用

写一个程序, 5s, 10s后能定时执行一个任务,同时能不停的处理来的消息. ------------------------------------------------------------------------------------------------- package main import ( "fmt" "time" ) func main() { input := make(chan interface{}) //producer - pr

C#中WebService 的 Timer定时器过段时间后自动停止运行

我用.net做的一个Timer定时器,定时获取短信并给予回复,但大概过了十几个小时以后,Timer定时器会自动停止,再发送短信就不能收到回复,需要在服务器中重新运行定时器才可以,请教各位! 我是在.net framework中的,有一个Global.asax全局应用程序文件,帖代码:public class Global : System.Web.HttpApplication { double iTimerInterval; System.Timers.Timer timer = new Sy

[ Javascript ] JavaScript中的定时器(Timer) 是如何工作的!

作为入门者来说,了解JavaScript中timer的工作方式是很重要的.通常它们的表现行为并不是那么地直观,而这是因为它们都处在一个单一线程中.让我们先来看一看三个用来创建以及操作timer的函数. var id = setTimeout(fn, delay); - 初始化一个单一的timer,这个timer将会在一定延时后去调用指定的函数.这个函数(setTimeout)将返回一个唯一的ID,我们可以通过这个ID来取消timer. var id = setInterval(fn, delay

基于c#中Timer实现定时器功能

在c#中关于定时器类就有三个 定义在System.Windows.Forms里 System.Windows.Forms.Timer是应用于WinForm中的,它是通过Windows消息机制实现的,类似于VB或Delphi中的Timer控件,内部使用API SetTimer实现的.它的主要缺点是计时不精确,而且必须有消息循环,Console Application(控制台应用程序)无法使用 定义在System.Threading.Timer类里 定义在System.Timers.Timer类里