新聞中心
在寫(xiě) Python 的時(shí)候,如果想讓某個(gè)函數(shù)每 60 秒執(zhí)行一次,我們一般這樣寫(xiě)代碼:

峨眉山網(wǎng)站制作公司哪家好,找成都創(chuàng)新互聯(lián)!從網(wǎng)頁(yè)設(shè)計(jì)、網(wǎng)站建設(shè)、微信開(kāi)發(fā)、APP開(kāi)發(fā)、響應(yīng)式網(wǎng)站建設(shè)等網(wǎng)站項(xiàng)目制作,到程序開(kāi)發(fā),運(yùn)營(yíng)維護(hù)。成都創(chuàng)新互聯(lián)公司2013年成立到現(xiàn)在10年的時(shí)間,我們擁有了豐富的建站經(jīng)驗(yàn)和運(yùn)維經(jīng)驗(yàn),來(lái)保證我們的工作的順利進(jìn)行。專(zhuān)注于網(wǎng)站建設(shè)就選成都創(chuàng)新互聯(lián)。
- import time
- while True:
- some_function()
- time.sleep(60)
于是,我在寫(xiě) Golang 代碼的時(shí)候,也使用了這種方式:
- package main
- import (
- "fmt"
- "time"
- )
- func someFunction() {
- fmt.Println("我是某個(gè)函數(shù)")
- }
- func main() {
- for {
- someFunction()
- time.Sleep(10 * time.Second)
- }
- }
今天在看同事的代碼時(shí),發(fā)現(xiàn)他是這樣寫(xiě)的:
- package main
- import (
- "fmt"
- "time"
- )
- func someFunction() {
- fmt.Println("我是某個(gè)函數(shù)")
- }
- func main() {
- tikcer := time.NewTicker(10 * time.Second)
- for {
- <-tikcer.C
- someFunction()
- }
- }
這種寫(xiě)法,初看起來(lái)時(shí)跟time.Sleep沒(méi)什么區(qū)別,但是仔細(xì)一想,卻發(fā)現(xiàn)它有很多優(yōu)勢(shì)。
首先,NewTicker會(huì)在背后計(jì)時(shí),時(shí)間到了以后,會(huì)向內(nèi)部的一個(gè) channel 中推入當(dāng)前的時(shí)間。然后繼續(xù)計(jì)時(shí)。所以,如果函數(shù)someFunction()執(zhí)行了3秒鐘。那么接下來(lái)過(guò)7秒就會(huì)繼續(xù)執(zhí)行。但如果使用time.Sleep,函數(shù)執(zhí)行完成以后,還要再等10秒鐘才會(huì)執(zhí)行。
其次,如果不啟動(dòng)新的協(xié)程,那么當(dāng)執(zhí)行到time.Sleep時(shí),整個(gè)程序是卡住的,必須等待它結(jié)束了才能執(zhí)行后面的操作。但如果使用 NewTicker,那么在等待的時(shí)間,還可以做很多其他的事情。多個(gè)不同的定時(shí)器可以同時(shí)工作:
- package main
- import (
- "fmt"
- "time"
- )
- func someFunction() {
- fmt.Println("我是某個(gè)函數(shù)")
- }
- func anotherFunction() {
- fmt.Println("另一個(gè)函數(shù)")
- }
- func thirdFunction() {
- fmt.Println("第三個(gè)函數(shù)")
- }
- func main() {
- tikcer1 := time.NewTicker(10 * time.Second)
- tikcer2 := time.NewTicker(5 * time.Second)
- tikcer3 := time.NewTicker(3 * time.Second)
- for {
- select {
- case <-tikcer1.C:
- someFunction()
- case <-tikcer2.C:
- anotherFunction()
- case <-tikcer3.C:
- thirdFunction()
- }
- }
- }
這樣可以實(shí)現(xiàn),每3秒執(zhí)行 thirdFunction函數(shù),每5秒執(zhí)行anotherFunction,每10秒執(zhí)行一次someFunction。大家可以考慮一下,如何用 time.Sleep來(lái)實(shí)現(xiàn)這樣的功能。
注意每個(gè)函數(shù)都是獨(dú)立計(jì)時(shí)的,只要他們執(zhí)行的時(shí)間不超過(guò)他們間隔的時(shí)間,就不會(huì)互相影響。
除了全部用來(lái)計(jì)時(shí)外,我們還可以用來(lái)設(shè)置外部開(kāi)關(guān),中斷一個(gè)協(xié)程。例如:
- package main
- import (
- "fmt"
- "time"
- )
- func doSomething() {
- fmt.Println("進(jìn)行某些操作")
- }
- func someFunction(stop chan bool) {
- fmt.Println("我是某個(gè)函數(shù)")
- tikcer1 := time.NewTicker(10 * time.Second)
- for {
- select {
- case <-tikcer1.C:
- doSomething()
- case <-stop:
- return
- }
- }
- }
- func main() {
- stop := make(chan bool)
- go someFunction(stop)
- //很多行代碼
- //很多行代碼
- //很多行代碼
- stop <- true
- //其他代碼
- //其他代碼
- }
在協(xié)程里面是一個(gè)10秒執(zhí)行一次的定時(shí)函數(shù)。但是我們可以在外面控制這個(gè)協(xié)程,從而隨時(shí)停止這個(gè)協(xié)程。
本文轉(zhuǎn)載自微信公眾號(hào)「未聞Code」,可以通過(guò)以下二維碼關(guān)注。轉(zhuǎn)載本文請(qǐng)聯(lián)系未聞Code公眾號(hào)。
本文名稱(chēng):TickerOrSleep?定時(shí)執(zhí)行的新選擇
網(wǎng)站網(wǎng)址:http://www.5511xx.com/article/cdspidg.html


咨詢(xún)
建站咨詢(xún)
