channels

在开始之前,让我们先回忆一下。我们都知道,一个 Go 程的存活周期是建立在 main 进程之上的,举个例子:

package main

import "fmt"

func main() {
    go func() {
        fmt.Println("hello there")
    }()
}
fmt.Printlnmain()Waitgroup
package main

import (
    "fmt"
    "sync"
)

func main() {
    var wg sync.WaitGroup
    defer wg.Wait()
    wg.Add(1)
    go func() {
        defer wg.Done()
        fmt.Println("hello there")
    }()
}

好的,现在让我们进入今天的正题,我们想在 Go 程中通过管道发送信息,很简单吧?

package main

import "fmt"

func main() {
    c := make(chan string)

    go func() {
        c <- "hello there"
    }()

    msg := <- c
    fmt.Println(msg)
}
WaitGroupchannelchannelgoroutine
chanenlstringsrangechannel
package main

import "fmt"

func main() {
    c := make(chan string)

    go func() {
        for i := 0; i < 10; i++ {
            c <- "hello there"
        }
    }()

    for msg := range c {
        fmt.Println(msg)
    }
}

结果比较因缺思厅:

hello there
hello there
hello there
hello there
hello there
hello there
hello there
hello there
hello there
hello there
fatal error: all Goroutines are asleep - deadlock!

goroutine 1 [chan receive]:
main.main()
    /tmp/sandbox697910326/main.go:14 +0x120
rangechannelchannelchannel
package main

import "fmt"

func main() {
    c := make(chan string)

    go func() {
        for i := 0; i < 10; i++ {
            c <- "hello there"
        }
        close(c)
    }()
    for msg := range c {
        fmt.Println(msg)
    }
}
close
forgoroutines
package main

import "fmt"

func main() {
    c := make(chan string)

    for i := 0; i < 10; i++ {
        go func() {
            c <- "hello there"
        }()
        close(c)
    }
    for msg := range c {
        fmt.Println(msg)
    }
}

结果:

panic: close of closed channel

goroutine 1 [running]:
main.main()
    /tmp/sandbox536323156/main.go:12 +0xa0
channelchannelpanic
goroutine
package main

import (
    "fmt"
    "sync"
)

func main() {
    var wg sync.WaitGroup
    defer wg.Wait()

    c := make(chan string)

    for i := 0; i < 10; i++ {
        wg.Add(1)
        go func() {
            defer wg.Done()
            c <- "hello there"
        }()
    }

    go func() {
        for msg := range c {
            fmt.Println(msg)
        }
    }()
}
goroutinesfor / Gogoroutine

我写这篇文章也是为了做一个自我梳理,让自己的思路更清晰一些,所以如果你发现任何不正确不到位的讲解说明,请不要犹豫,赶快在下面评论吧。


本文由 原创编译, 荣誉推出