在 go Channel 中尝试 Range 和 Close
Trying out Range and Close in go Channel
我正在尝试在通道中使用 range 和 close 来更好地理解它。
以下是我根据自己的理解尝试的代码示例。
执行下面的代码后,出现代码下面提到的错误。
代码:
package main
import (
"fmt"
)
func main() {
str := "hello"
hiChannel := make(chan string, 5)
for j := 1; j <= 5; j++ {
go func(hi string) {
hiChannel <- hi
}(str)
}
defer close(hiChannel)
for s := range hiChannel {
fmt.Println(s)
}
}
错误:
go run restsample/restsample.go
hello
hello
hello
hello
hello
fatal error: all goroutines are asleep - deadlock!
goroutine 1 [chan receive]:
main.main()
C:/Users/Indian/personal/Workspaces/Learning/src/restsample/restsample.go:16 +0x169
exit status 2
for s := range hiChannel
当您关闭 hiChannel
时 for 语句退出,实际上您并没有关闭通道,因此,您的代码引发了死锁。
关闭通道的方式有多种,比如可以统计打印了多少个字符串,然后关闭通道。
或者您可以创建信号通道并在收到所有必要信息后关闭。
根据@Tinwor 的反馈,我尝试添加几行来检查消息计数并且成功了。谢谢
package main
import (
"fmt"
)
func main() {
str := "hello"
hiChannel := make(chan string, 5)
for j := 1; j <= 5; j++ {
go func(hi string) {
hiChannel <- hi
}(str)
}
i := 1
for s := range hiChannel {
i++
if i == 5 {
fmt.Println(s)
close(hiChannel)
} else {
fmt.Println(s)
}
}
}
我正在尝试在通道中使用 range 和 close 来更好地理解它。 以下是我根据自己的理解尝试的代码示例。
执行下面的代码后,出现代码下面提到的错误。
代码:
package main
import (
"fmt"
)
func main() {
str := "hello"
hiChannel := make(chan string, 5)
for j := 1; j <= 5; j++ {
go func(hi string) {
hiChannel <- hi
}(str)
}
defer close(hiChannel)
for s := range hiChannel {
fmt.Println(s)
}
}
错误:
go run restsample/restsample.go
hello
hello
hello
hello
hello
fatal error: all goroutines are asleep - deadlock!
goroutine 1 [chan receive]:
main.main()
C:/Users/Indian/personal/Workspaces/Learning/src/restsample/restsample.go:16 +0x169
exit status 2
for s := range hiChannel
当您关闭 hiChannel
时 for 语句退出,实际上您并没有关闭通道,因此,您的代码引发了死锁。
关闭通道的方式有多种,比如可以统计打印了多少个字符串,然后关闭通道。
或者您可以创建信号通道并在收到所有必要信息后关闭。
根据@Tinwor 的反馈,我尝试添加几行来检查消息计数并且成功了。谢谢
package main
import (
"fmt"
)
func main() {
str := "hello"
hiChannel := make(chan string, 5)
for j := 1; j <= 5; j++ {
go func(hi string) {
hiChannel <- hi
}(str)
}
i := 1
for s := range hiChannel {
i++
if i == 5 {
fmt.Println(s)
close(hiChannel)
} else {
fmt.Println(s)
}
}
}