Go中的并发和超时

这个围棋程序:


package main


import (

    "fmt"

    "time"

)


func main() {

    start := time.Now()


    sleep_durations := []int{8100, 1000, 2500, 500, 6000}

    // sleep_durations := []int{8100, 1000, 2500, 500}

    c := make(chan string)

    defer close(c) // close channel when main exits

    for index, duration := range sleep_durations {

        go sleepy(fmt.Sprintf("sleepy%d: ", index+1), duration, c)

    }

    fmt.Printf("starting %d sleepys\n", len(sleep_durations))


    for range sleep_durations {

        select {

        case msg := <-c:

            fmt.Println("received: ", msg)

        case <-time.After(time.Second * time.Duration(5)):

            fmt.Println("*** TIMEOUT ***")

        }

    }


    elapsed := time.Since(start)

    fmt.Printf("... %d sleepys ran in: %e\n", len(sleep_durations), elapsed.Seconds())

}


func sleepy(msg string, sleep_ms int, yawn chan string) {

    start := time.Now()

    sleep := time.Duration(sleep_ms) * time.Millisecond

    time.Sleep(sleep) // some sleepy work

    yawn <- fmt.Sprintf("%s slept for %s", msg, sleep)

    elapsed := time.Since(start)

    fmt.Printf("\t%s finished in: %s\n", msg, elapsed)

}

https://play.golang.org/p/0ioTuKv230


有令人困惑的结果。当第 11 行被取消注释时,它不会按预期工作,即time.After5 秒不会发生。但是在第 11 行注释和第 12 行取消注释后,超时确实按预期工作。我是 Go 的新手,但我错过了什么?


慕森卡
浏览 146回答 2
2回答

海绵宝宝撒

我找到了我要找的东西:package mainimport (&nbsp; "fmt"&nbsp; "sync"&nbsp; "time")func main() {&nbsp; var wg sync.WaitGroup&nbsp; done := make(chan struct{})&nbsp; wq := make(chan interface{})&nbsp; worker_count := 2&nbsp; for i := 0; i < worker_count; i++ {&nbsp; &nbsp; wg.Add(1)&nbsp; &nbsp; go doit(i, wq, done, &wg)&nbsp; }&nbsp; fmt.Printf("doing work\n")&nbsp; for i := 0; i < worker_count; i++ {&nbsp; &nbsp; time.Sleep(time.Millisecond * time.Duration(100))&nbsp; &nbsp; wq <- fmt.Sprintf("worker: %d", i)&nbsp; }&nbsp; fmt.Printf("closing 'done' channel\n")&nbsp; close(done)&nbsp; fmt.Printf("block/wait until all workers are done\n")&nbsp; wg.Wait()&nbsp; fmt.Println("all done!")}func doit(worker_id int, wq <-chan interface{}, done <-chan struct{}, wg *sync.WaitGroup) {&nbsp; fmt.Printf("[%v] is working\n", worker_id)&nbsp; defer wg.Done()&nbsp; max_time := time.Second * time.Duration(5)&nbsp; for {&nbsp; &nbsp; select {&nbsp; &nbsp; case m := <-wq:&nbsp; &nbsp; &nbsp; fmt.Printf("[%v] m => %v\n", worker_id, m)&nbsp; &nbsp; case <-done:&nbsp; &nbsp; &nbsp; fmt.Printf("[%v] is done\n", worker_id)&nbsp; &nbsp; &nbsp; return&nbsp; &nbsp; case <-time.After(max_time):&nbsp; &nbsp; &nbsp; fmt.Printf("timeout > %s seconds!\n", max_time)&nbsp; &nbsp; }&nbsp; }}
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Go