我想并行读取多个文件,但遇到了死锁。
package main
import (
"bufio"
"os"
"strings"
)
func main() {
var dirname = "."
res := make(chan string)
dir, _ := os.Open(dirname)
files, _ := dir.ReadDir(10)
filecnt := 0
for _, file := range files {
var idx = strings.Index(file.Name(), "input_")
if idx == 0 {
filecnt++
go readFile(dirname+"/"+file.Name(), res)
}
}
donecnt := 0
for donecnt < filecnt {
for s := range res {
if s == "" {
donecnt++
}
}
}
close(res)
}
func readFile(filename string, res chan string) {
file, _ := os.Open(filename)
defer file.Close()
scanner := bufio.NewScanner(file)
for scanner.Scan() {
res <- scanner.Text()
}
res <- ""
}
它会在
range res
处阻塞,因为这会等到通道关闭。读取完所有文件后如何关闭通道?有更好的方法吗?
您可以使用 Golang 的 WaitGroups 更有效地实现这一点。
以下是如何使用 WaitGroups 编写相同的代码:
package main
import (
"os"
"strings"
"sync"
)
var wg sync.WaitGroup
func main() {
var dirname = "."
dir, _ := os.Open(dirname)
files, _ := dir.ReadDir(10)
for _, file := range files {
var idx = strings.Index(file.Name(), "input_")
if idx == 0 {
wg.Add(1)
go readFile(dirname+"/"+file.Name(), res)
}
}
// Wait for all goroutines to signal they are done.
wg.Done()
}
func readFile(filename string, res chan string) {
defer wg.Done()
// Your logic to read file.
}