package mainimport fmt timefunc main ch = makechan int 5 for i = 0; i 10; i++ go funci int ch - i fmtPrintlni i timeSleep3 timeSecond closech timeSleep3 timeSecond这段代码有什么问题
这段代码存在以下问题:
-
代码中的goroutine会向channel发送数据,但是没有其他goroutine来接收数据。这会导致程序在发送第6个元素到channel时阻塞,并导致死锁。
-
在主函数中,通过time.Sleep()函数来等待一段时间后关闭channel。这是一种不可靠的方式,因为无法确保所有的goroutine都已经完成。如果某个goroutine需要更长的时间才能完成,那么关闭channel的操作可能会在该goroutine完成之前发生,导致数据丢失。
解决方法:
-
使用一个计数器来追踪所有的goroutine是否已经完成。可以使用sync.WaitGroup来实现这个功能。
-
在主函数中,使用sync.WaitGroup的Wait()方法来等待所有的goroutine完成。
-
在goroutine中,使用defer语句来通知sync.WaitGroup,该goroutine已经完成。
改进后的代码如下:
package main
import ( "fmt" "sync" "time" )
func main() { ch := make(chan int, 5) wg := sync.WaitGroup{} wg.Add(10)
for i := 0; i < 10; i++ {
go func(i int) {
defer wg.Done()
ch <- i
fmt.Println(i)
}(i)
}
wg.Wait()
close(ch)
time.Sleep(3 * time.Second)
原文地址: https://www.cveoy.top/t/topic/iqcr 著作权归作者所有。请勿转载和采集!