golang 定时器封装——支持超时和函数自定义

golang 定时器封装——支持超时和函数自定义
强烈推介IDEA2020.2破解激活,IntelliJ IDEA 注册码,2020.2 IDEA 激活码

如标题,封装一个golang的定时器,能够设置超时时间和定时器的interval。开启定时器后使用一个新的goroutine进行倒计时操作。

好,下面上货。

package common

import (
	"context"
	"fmt"
	"github.com/google/uuid"
	"go.uber.org/atomic"
	"time"
)

const (
	STOP    = 0
	RUNNING = 1
)

type ClockCountDown struct {
	clockId  string //clock标识
	timeout  int64  //超时秒数
	interval int64  //间隔秒数
	ticker   *time.Ticker
	flag     *atomic.Int32 //是否运行
}

//新建一个定时器
func NewClockCountDown(timeout, interval int64) ClockCountDown {
	tmpTicker := time.NewTicker(time.Duration(interval) * time.Second)
	return ClockCountDown{
		clockId:  uuid.New().String(),
		timeout:  timeout,
		interval: interval,
		ticker:   tmpTicker,
		flag:     atomic.NewInt32(0),
	}
}

/**
开始倒计时
 */
func (ccd *ClockCountDown) StartCountDown(intervalFunc func(param interface{}) bool, param1 interface{}, overFunc func(param interface{}), param2 interface{}) {
	if ccd.flag.CAS(STOP, RUNNING) {
		fmt.Printf("clockcountdown start:%s\n", ccd.clockId)
		go ccd.start(intervalFunc, param1, overFunc, param2)
	} else {
		fmt.Printf("clockcountdown already start:%s,can not start more than twice\n", ccd.clockId)
	}
}

/**
intervalFunc 每次执行函数
overFunc 超时/结束执行函数,如果返回false,则会停止定时器
 */
func (ccd *ClockCountDown) start(intervalFunc func(param interface{}) bool, param1 interface{}, overFunc func(param interface{}), param2 interface{}) {
	defer ccd.ticker.Stop()
	rootCtx := context.Background()
	ctx, cancelFunc := context.WithTimeout(rootCtx, time.Duration(ccd.timeout)*time.Second)
	for {
		select {
		case <-ctx.Done():
			fmt.Printf("clockCountDown Done:%s!\n", ccd.clockId)
			cancelFunc()
			if overFunc != nil {
				overFunc(param2)
			}
			return
		case <-ccd.ticker.C:
			if intervalFunc != nil {
				if !intervalFunc(param1) {
					cancelFunc()
				}
			}
		}
	}
}

 

在main函数中测试一下效果:

package main

import (
	"context"
	"etcdclient/src/common"
	"fmt"
	"sync"
	"time"
)

func main() {
	ccd := common.NewClockCountDown(10, 1)
	ccd.StartCountDown(p, "abcd", q, "bbbbb")
	ccd.StartCountDown(p, "abcd", q, "bbbbb")
	stopTheWorld()
}

func p(param interface{}) bool {
	//做一下转换 param抓换成自己需要的类型即可。
	fmt.Printf("clock_common running Current time: %v,%s\n", time.Now(), param)
	return true
}

func q(param interface{}) {
	//做一下转换 param抓换成自己需要的类型即可。
	fmt.Printf("clock_common down Current time: %v,%s\n", time.Now(), param)
}

运行效果:

clockcountdown start:56bc7589-0a94-4216-9cdb-da8f5815f42a
clockcountdown already start:56bc7589-0a94-4216-9cdb-da8f5815f42a,can not start more than twice
clock_common running Current time: 2020-01-07 12:12:05.486255 +0800 CST m=+1.005142040,abcd
clock_common running Current time: 2020-01-07 12:12:06.489267 +0800 CST m=+2.008080035,abcd
clock_common running Current time: 2020-01-07 12:12:07.485208 +0800 CST m=+3.004031462,abcd
clock_common running Current time: 2020-01-07 12:12:08.487824 +0800 CST m=+4.006562295,abcd
clock_common running Current time: 2020-01-07 12:12:09.489621 +0800 CST m=+5.008359055,abcd
clock_common running Current time: 2020-01-07 12:12:10.490092 +0800 CST m=+6.008756465,abcd
clock_common running Current time: 2020-01-07 12:12:11.486778 +0800 CST m=+7.005367140,abcd
clock_common running Current time: 2020-01-07 12:12:12.487973 +0800 CST m=+8.006561740,abcd
clock_common running Current time: 2020-01-07 12:12:13.489144 +0800 CST m=+9.007658675,abcd
clock_common running Current time: 2020-01-07 12:12:14.487543 +0800 CST m=+10.006058417,abcd
clockCountDown Done:56bc7589-0a94-4216-9cdb-da8f5815f42a!
clock_common down Current time: 2020-01-07 12:12:14.487746 +0800 CST m=+10.006260827,bbbbb

需要注意,如果intervalFunc返回false,那么定时器会结束,不再继续执行。这样能够达到通过定时器内部逻辑控制定时器是否继续执行的目的。

本文来源0day__,由javajgs_com转载发布,观点不代表Java架构师必看的立场,转载请标明来源出处:https://javajgs.com/archives/8083

发表评论