美文网首页
golang-定时器

golang-定时器

作者: 爱吃豆包 | 来源:发表于2020-02-03 23:16 被阅读0次

    定时器 和 断续器

    定时器:延时某些操作任务
    断续器:设置的好间隔时间,周而复始的执行任务

    package main
    
    import (
        "fmt"
        "time"
    )
    
    // 定时器  和 断续器
    /**
    
        定时器:延时某些操作任务
        断续器:设置的好间隔时间,周而复始的执行任务
    
        有两种方式创建定时器:
            time.NewTimer 函数 和 time.AfterFunc 函数
            这两个函数将得到 time.Timer 类型
    
            // timer.Reset(time.Second * 3) 重置定时器,并设置定时器间隔时间
            // timer.Stop() 停止定时器
            // time.Sleep(time.Second) // 睡眠,一秒
    
            timer.Reset(...) 和 timer.Sleep() 返回值是一个 bool 值。
            如果值为 false 表示,这个定时器已经过期(或者结束了),
            如果值为 true 表示,已经成功 重置 或者 停止
    
    
            time.NewTimer 函数 和 time.AfterFunc 函数 创建的定时器只能执行一次,
            需要配合 for 和 select 才能周而复始的执行
    
    
        断续器:
            time.NewTicker 函数创建, 可以周而复始的执行,比如每次间隔3秒执行一次任务
    
    **/
    
    // ========================  定时器
    
    // 定时器例子 time.NewTimer 方式
    func timer1() {
    
        // 这里的定时器,执行完就会结束(因为main函数结束了),如果想周而复始的执行,使用 for 和 select 方式
    
        // 创建一个到期时间的间隔为 3 秒的定时器
        // 参数 time.Duration 类型
        timer := time.NewTimer(time.Second * 3)
        fmt.Printf("定时器开始时间:%v\n", time.Now().Format("2006-01-02 15:04:05"))
        // <-timer.C 表示接收这个管道的值, 传递过来的是它到期的时间
    
        // 间隔一段时间执行下面的代码, 管道有值表示定时器的执行任务的时间到了
        expTime := <-timer.C
        fmt.Printf("定时器结束时间:%v\n", time.Now().Format("2006-01-02 15:04:05"))
        // 指定自定义的时间进行格式化
        // time.Parse("2006-01-02 15:04:05", "2020-10-01 10:10:01")
        fmt.Printf("接收定时器管道的值:%v", expTime.Format("2006-01-02 15:04:05"))
        fmt.Printf("停止定时器:%v", timer.Stop())
    
        // timer.Reset(time.Second * 3) 重置定时器,并设置定时器间隔时间
        // timer.Stop() 停止定时器
        // time.Sleep(time.Second) // 睡眠,一秒
    }
    
    // 定时器例子 time.AfterFunc 方式
    func timer2() {
        // 这里的定时器,执行完就会结束(因为main函数结束了),如果想周而复始的执行,使用 select 方式
    
        // 创建一个到期时间的间隔为 3 秒的定时器
        time.AfterFunc(time.Second*3, func() {
            // 我需要执行操作...
            fmt.Printf("定时器执行中!")
        })
    
        // time.AfterFunc 函数不会往 C <- timer.C 管道中发送数据,而是启用 goroutine 去执行传递进去的函数
    }
    
    // 定时器例子
    // 上面的例子,会发现只执行了一次,
    // 这个例子适用于指定我们需要执行的次数
    // 这里使用 time.NewTimer 做例子
    func timer3() {
    
        t := time.Second * 3
        var timer *time.Timer
    
        // 执行任务的通信管道
        intChan := make(chan int, 1)
        go func() {
            // 设置需要执行次数
            // 比如只需执行两次
            for i := 0; i < 2; i++ {
                intChan <- i
                time.Sleep(time.Second)
            }
            // 关闭这个管道
            close(intChan)
        }()
    
        for {
            if timer == nil {
                timer = time.NewTimer(t)
            } else {
                // 通过 timer.Reset 函数重置这个定时器,达到目的
                // 将超时时间重置
                timer.Reset(t)
            }
    
            // 堵塞,谁有数据,就执行谁
            // 只会执行一次
            // 如果配合 for 死循环,可以达到一直监听管道的目的
            select {
            case e, ok := <-intChan:
                // 如果管道关闭,表示这个 intChan 管道不可用使用,那么这个 ok 就是 false
                if !ok {
                    // 结束这个定时器
                    return
                }
                fmt.Printf("定时器正在执行任务!时间:%v\t, 管道值:%v\n", time.Now().Format("2006-01-02 15:04:05"), e)
            case <-timer.C:
                // 如果 intChan 超过 3秒 没有数据,则会执行
                fmt.Printf("超时!\n")
            }
        }
    
    }
    
    // 定时器例子,达到 断续器 的效果,周而复始执行
    func timer4() {
        t := time.Second * 3
        var timer *time.Timer
    
        for {
            if timer == nil {
                timer = time.NewTimer(t)
            } else {
                // 通过 timer.Reset 函数重置这个定时器,达到目的
                // 将超时时间重置
                timer.Reset(t)
            }
    
            // 堵塞,谁有数据,就执行谁
            // 只会执行一次
            // 如果配合 for 死循环,可以达到一直监听管道的目的
            select {
            case <-timer.C:
                fmt.Printf("执行任务,当前时间:%v\n", time.Now().Format("2006-01-02 15:04:05"))
            }
        }
    }
    
    // ======================  断续器
    
    // 周而复始的执行
    func timer5() {
        ticker := time.NewTicker(time.Second * 3)
        for {
            select {
            case <-ticker.C:
                fmt.Printf("执行任务,当前时间:%v\n", time.Now().Format("2006-01-02 15:04:05"))
            }
        }
        // ticker.Stop() 停止断续器
    }
    
    func main() {
        go timer4()
    
        // 主线程 睡眠 10 秒
        time.Sleep(time.Second * 10)
    
    }
    
    

    相关文章

      网友评论

          本文标题:golang-定时器

          本文链接:https://www.haomeiwen.com/subject/dullxhtx.html