【问题标题】:Using goroutines to iterate through file indefinitely使用 goroutine 无限期地遍历文件
【发布时间】:2021-12-31 06:18:30
【问题描述】:

我是 Go 新手,请原谅我的无知。我正在尝试使用 goroutine 无限期地逐行迭代一堆单词列表。但是当尝试这样做时,它不会迭代或中途停止。在不中断流程的情况下,我将如何以适当的方式解决这个问题?

package main

import (
    "bufio"
    "fmt"
    "os"
)


var file, _ = os.Open("wordlist.txt")
func start() {
    scanner := bufio.NewScanner(file)
    for scanner.Scan() {
       fmt.Println(scanner.Text())
    }

}

func main(){
    for t := 0; t < 150; t++ {
        go start()
        fmt.Scanln()
    }
}

谢谢!

【问题讨论】:

  • for t := 0; t &lt; 150这行是什么意思?
  • 我试图生成多个 goroutine,它们将无限迭代文本文件,直到条件为真。我没说对,对不起!

标签: loops file go iteration goroutine


【解决方案1】:

您将file 声明为全局变量。在多个 goroutine 之间共享读/写文件状态是一种数据竞争,会给你带来不确定的结果。

最有可能的是,读取从任何 goroutine 的最后一次读取停止的地方开始。如果那是文件结尾,它可能继续是文件结尾。但是,由于结果未定义,因此无法保证。您的不稳定结果是由于未定义的行为造成的。

这是您的程序的修订版本,它声明了一个本地 file 变量并使用 sync.Waitgroup 来同步所有 go start() goroutine 和 main goroutine 的完成。程序检查错误。

package main

import (
    "bufio"
    "fmt"
    "os"
    "sync"
)

func start(filename string, wg *sync.WaitGroup, t int) {
    defer wg.Done()

    file, err := os.Open(filename)
    if err != nil {
        fmt.Println(err)
        return
    }
    defer file.Close()

    lines := 0
    scanner := bufio.NewScanner(file)
    for scanner.Scan() {
        lines++
    }
    if err := scanner.Err(); err != nil {
        fmt.Println(err)
        return
    }
    fmt.Println(t, lines)
}

func main() {
    wg := &sync.WaitGroup{}
    filename := "wordlist.txt"
    for t := 0; t < 150; t++ {
        wg.Add(1)
        go start(filename, wg, t)
    }
    wg.Wait()
}

【讨论】:

  • 是的,但是,正如我的回答所示,为什么在这种情况下使用 goroutine?
  • @VonC:OP 说“我正在尝试使用 goroutine 无限期地逐行遍历一堆单词列表。”我假设“一堆”意味着他有几个要同时迭代的词表。 OP 的代码显然是 MRE,而不是实际代码。例如,使用fmt.Scanln() 暂时停止执行,可能是为了调试。
  • 同意。这就是为什么我提到play.golang.org/p/EUB0K2V7iT 作为并发列表扫描的一个例子。
  • @VonC:哇!这是一个复杂的例子 (play.golang.org/p/EUB0K2V7iT),它没有直接解决 OP 的问题:为什么我的代码不起作用?
  • 当然:我确实解释了为什么 OP 的代码不起作用:缺乏同步。而且,在 OP 特定的情况下,不需要 goroutine。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-01-06
  • 2016-11-26
  • 1970-01-01
  • 2019-11-06
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多