> 백엔드 개발 > Golang > Go 언어에서 타이머를 설정하는 방법

Go 언어에서 타이머를 설정하는 방법

藏色散人
풀어 주다: 2020-12-17 16:37:30
원래의
4869명이 탐색했습니다.

Go 언어에서 타이머를 설정하는 방법: 1. 설정된 간격에 따라 티커가 트리거되는 "time.NewTicker()" 메서드를 통해 생성합니다. 2. "time.NewTimer()를 통해 생성합니다. 타이머만 단어를 실행하는 " 메소드 3. "After()"를 사용하여 생성합니다.

Go 언어에서 타이머를 설정하는 방법

이 글의 환경: Windows 7 시스템, Go1.11.2 버전, 이 글은 모든 브랜드의 컴퓨터에 적용됩니다.

추천: "golang 튜토리얼"

Go 언어의 타이머 사용

GO 언어는 시간 패키지에서 타이머를 사용하는 세 가지 방법을 제공합니다:

1. 첫 번째 유형 : ticker

// A Ticker holds a channel that delivers `ticks' of a clock
// at intervals.
type Ticker struct {
	C <-chan Time // The channel on which the ticks are delivered.
	r runtimeTimer
}
로그인 후 복사

time.NewTicker()를 통해 생성됩니다. 이 유형에서는 작업이 적극적으로 종료되지 않는 한 설정된 간격에 따라 티커가 계속 트리거됩니다.

2. 두 번째 유형: timer

// The Timer type represents a single event.
// When the Timer expires, the current time will be sent on C,
// unless the Timer was created by AfterFunc.
// A Timer must be created with NewTimer or AfterFunc.
type Timer struct {
	C <-chan Time
	r runtimeTimer
}
로그인 후 복사

time.NewTimer()을 통해 생성됩니다. 물론 타이머는 한 번만 실행됩니다. timer.Reset()을 호출하여 타이머를 다시 작동시키고 간격을 변경할 수 있습니다.

3. 세 번째 유형: After()

// After waits for the duration to elapse and then sends the current time
// on the returned channel.
// It is equivalent to NewTimer(d).C.
// The underlying Timer is not recovered by the garbage collector
// until the timer fires. If efficiency is a concern, use NewTimer
// instead and call Timer.Stop if the timer is no longer needed.
func After(d Duration) <-chan Time {
	return NewTimer(d).C
}
로그인 후 복사

코드에서 볼 수 있듯이 After()는 실제로 Timer의 구문 설탕입니다.


다음은 코드를 통해 세 가지 메서드를 사용하는 방법을 보여줍니다.

1.Ticker

ticker := time.NewTicker(time.Second * 1) // 运行时长
    ch := make(chan int)
    go func() {
        var x int
        for x < 10 {
            select {
            case <-ticker.C:
                x++
                fmt.Printf("%d\n", x)
            }
        }
        ticker.Stop()
        ch <- 0
    }()
    <-ch                                    // 通过通道阻塞,让任务可以执行完指定的次数。
로그인 후 복사

티커는 1초마다 트리거됩니다. 즉, 매초마다 하나의 콘텐츠가 Ticker.C에 추가됩니다. 마지막으로 ch에 숫자를 써서 프로그램 차단을 해제하고 실행을 계속합니다.

2.Timer

timer := time.NewTimer(time.Second * 1) // timer 只能按时触发一次,可通过Reset()重置后继续触发。
    go func() {
        var x int
        for {
            select {
            case <-timer.C:
                x++
                fmt.Printf("%d,%s\n", x, time.Now().Format("2006-01-02 15:04:05"))
                if x < 10 {
                    timer.Reset(time.Second * 2)
                } else {
                    ch <- x
                }
            }
        }
    }()
    <-ch
로그인 후 복사

3.After()

// 阻塞一下,等待主进程结束
    tt := time.NewTimer(time.Second * 10)
    <-tt.C
    fmt.Println("over.")

    <-time.After(time.Second * 4)
    fmt.Println("再等待4秒退出。tt 没有终止,打印出 over 后会看见在继续执行...")
    tt.Stop()
    <-time.After(time.Second * 2)
    fmt.Println("tt.Stop()后, tt 仍继续执行,只是关闭了 tt.C 通道。")
로그인 후 복사

4. 이러한 기본 방법을 사용하여 자체 예약 작업 관리를 설계할 수 있습니다.

type jobFunc2 func(j *job)

type job struct {
    jf     jobFunc2
    params map[string]interface{}
    ch     chan int
}

func NewJob() *job {
    return &job{
        params: make(map[string]interface{}),
        ch:     make(chan int),
    }
}

func (j *job) Run(t time.Duration) {
    ticker := time.NewTicker(time.Second * t)
    go func() {
        for {
            select {
            case <-ticker.C:
                j.jf(j)
            case <-j.ch:
                fmt.Println("收到结束指令")
                ticker.Stop()
                break
            }
        }
    }()

}

func main() {
    j := NewJob()
    j.jf = func(jj *job) {
        fmt.Println("定时任务执行...", time.Now().Format("15:04:05 2006-02-01"), jj.params)
    }
    j.params["p1"] = "第一个参数"
    j.params["p2"] = 100
    j.Run(1)

    // 阻塞一下,等待主进程结束
    tt := time.NewTimer(time.Second * 10)
    <-tt.C
    fmt.Println("over.")

    <-time.After(time.Second * 4)
    fmt.Println("再等待4秒退出。tt 没有终止,打印出 over 后会看见在继续执行...")
    tt.Stop()
    <-time.After(time.Second * 2)
    fmt.Println("tt.Stop()后, tt 仍继续执行,只是关闭了 tt.C 通道。")
}
로그인 후 복사

일부 실행 결과 스크린샷:

마지막으로 작업 실행이 채널을 통해 종료된다는 점을 덧붙이고 싶습니다.

// 阻塞一下,等待主进程结束
    tt := time.NewTimer(time.Second * 10)
    <-tt.C
    fmt.Println("over.")

    <-time.After(time.Second * 4)
    fmt.Println("再等待4秒退出。tt 没有终止,打印出 over 后会看见在继续执行...")
    tt.Stop()
    <-time.After(time.Second * 2)
    fmt.Println("tt.Stop()后, tt 仍继续执行,只是关闭了 tt.C 通道。")
    j.ch <- 0
    <-time.After(time.Second * 2)
    fmt.Println("又等了2秒钟...这两秒钟可以看到 tt 没干活了...")
로그인 후 복사


GO 언어로 글을 쓸 때는 channel을 능숙하게 사용해야 합니다.

위 내용은 Go 언어에서 타이머를 설정하는 방법의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

관련 라벨:
원천:php.cn
본 웹사이트의 성명
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.
최신 이슈
인기 튜토리얼
더>
최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿