Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/go/7.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
goruntine不同时运行?_Go_Goroutine - Fatal编程技术网

goruntine不同时运行?

goruntine不同时运行?,go,goroutine,Go,Goroutine,我有下面的程序,我是gorountine的新手,我想测试的很简单,我在循环中调用gorountine 100次,如果有一次失败,整个程序失败,否则成功,fail10Percent它延迟1秒,如果是4,则检查一个随机数,让它失败 package main import ( "fmt" "math/rand" "time" ) func fail10Percent(ch chan int) { time.

我有下面的程序,我是gorountine的新手,我想测试的很简单,我在循环中调用gorountine 100次,如果有一次失败,整个程序失败,否则成功,
fail10Percent
它延迟1秒,如果是4,则检查一个随机数,让它失败

package main

import (
    "fmt"
    "math/rand"
    "time"
)

func fail10Percent(ch chan int) {
    time.Sleep(1 * time.Second)
    e := rand.Intn(10)
    fmt.Println("Calculating rand.Intn(10) ", e)

    if e == 4 {
        ch <- 0
        return
    }
    ch <- 1
}

func test() {
    for i := 0; i < 100; i++ {
        err := make(chan int)
        go fail10Percent(err)

        res := <-err

        fmt.Println("=== result: ", res)

        if res != 1 {
            fmt.Println("failed")
            return
        }
    }
    fmt.Println("succeeded")
}

func main() {
    test()
}

我已经为您注释了代码,以便您能够理解

package main

import (
    "fmt"
    "math/rand"
    "sync"
)

func fail10Percent(ch chan int, w *sync.WaitGroup) {
    defer w.Done()
    num := rand.Intn(10)
    fmt.Println("calculating rand.Intn(10) ", num)
    if num == 4 {
        ch <- 0 // Fail
        return
    }
    ch <- 1 // Pass
}

func test() {
    var ch = make(chan int, 1)
    // Launch the receiver goroutine to listen if goroutine succeeded or failed based on the value sent to ch
    go func() {
        for recv := range ch {
            switch recv {
            // Fail
            case 0:
                fmt.Println("goroutine failed")
            // Pass
            case 1:
                fmt.Println("goroutine succeed")
            }
        }
    }()
    // wg is a WaitGroup
    var wg sync.WaitGroup
    for i := 0; i < 100; i++ {
        wg.Add(1)
        go fail10Percent(ch, &wg)
    }
    // wg.Wait() to wait for all goroutines to complete
    wg.Wait()
    // Close the channel so that the receiver can stop
    close(ch)
}

func main() {
    test()
}

因为您使用的是无缓冲通道,所以main只需等待,直到它接收到通道上的内容。我建议您学习围棋和其他围棋基础知识。当goroutine失败时,整个程序都会失败,因为当您检查
res!=1
,您从测试函数返回,导致主goroutine退出,因此程序终止。
package main

import (
    "fmt"
    "math/rand"
    "sync"
)

func fail10Percent(ch chan int, w *sync.WaitGroup) {
    defer w.Done()
    num := rand.Intn(10)
    fmt.Println("calculating rand.Intn(10) ", num)
    if num == 4 {
        ch <- 0 // Fail
        return
    }
    ch <- 1 // Pass
}

func test() {
    var ch = make(chan int, 1)
    // Launch the receiver goroutine to listen if goroutine succeeded or failed based on the value sent to ch
    go func() {
        for recv := range ch {
            switch recv {
            // Fail
            case 0:
                fmt.Println("goroutine failed")
            // Pass
            case 1:
                fmt.Println("goroutine succeed")
            }
        }
    }()
    // wg is a WaitGroup
    var wg sync.WaitGroup
    for i := 0; i < 100; i++ {
        wg.Add(1)
        go fail10Percent(ch, &wg)
    }
    // wg.Wait() to wait for all goroutines to complete
    wg.Wait()
    // Close the channel so that the receiver can stop
    close(ch)
}

func main() {
    test()
}