代码段一,查询出产品 1767,打印出产品 1767
//查询产品列表
GetProductLst()
for _, pproductItem := range productLst.ProductItems {
fmt.Printf("产品编码 %v , 规格编号%v ,中文名称%v, 英文名称%v \n",
pproductItem.GoodsCode, pproductItem.SpecNo, pproductItem.GoodsCName,
pproductItem.GoodsEName)
}
代码段二
查询出1767,但每次打印出来结果不一样,有时打印1509条,有时打印1390条 , 有漏掉。
我的需求,查询 出来,用多线程打印,打印顺序可以不同,但条数不能漏掉,有没有什么办法 ?
func printProduct(pproductItem ProductItem) {
fmt.Printf("产品编码 %v , 规格编号%v ,中文名称%v, 英文名称%v \n", pproductItem.GoodsCode, pproductItem.SpecNo, pproductItem.GoodsCName,
pproductItem.GoodsEName)
}
func main() {
//查询产品列表
GetProductLst()
for _, pproductItem := range productLst.ProductItems {
go printProduct(pproductItem)
}
//暂停主线程
runtime.Gosched()
}
当你使用 Go 的多线程并发来打印输出时,可能会发现输出的结果不正确,有些行会漏掉或者顺序发生改变。这是因为 Go 的多线程并发执行是没有任何保证的,也就是说,你无法保证线程的执行顺序或者完整性。
有几种方法可以解决这个问题:
使用互斥锁(mutex)的代码示例:
import (
"fmt"
"sync"
)
var mu sync.Mutex
func printProduct(pproductItem ProductItem) {
mu.Lock()
defer mu.Unlock()
fmt.Printf("产品编码 %v , 规格编号%v ,中文名称%v, 英文名称%v \n", pproductItem.GoodsCode, pproductItem.SpecNo, pproductItem.GoodsCName,
pproductItem.GoodsEName)
}
func main() {
// 查询产品列表
GetProductLst()
for _, pproductItem := range productLst.ProductItems {
go printProduct(pproductItem)
}
}
使用通道(channel)的代码示例:
import (
"fmt"
)
func printProduct(pproductItem ProductItem, ch chan bool) {
fmt.Printf("产品编码 %v , 规格编号%v ,中文名称%v, 英文名称%v \n", pproductItem.GoodsCode, pproductItem.SpecNo, pproductItem.GoodsCName,
pproductItem.GoodsEName)
ch <- true
}
func main() {
ch := make(chan bool)
// 查询产品列表
GetProductLst()
for _, pproductItem := range productLst.ProductItems {
go printProduct(pproductItem, ch)
}
for range productLst.ProductItems {
<-ch
}
}