Golang: ファイル内の行数を効率的に判断するにはどうすればいいですか? 質問する

Golang: ファイル内の行数を効率的に判断するにはどうすればいいですか? 質問する

Golang で、ファイルの行数を効率的に判断する方法を探しています。

もちろん、ファイル全体をループすることもできますが、あまり効率的ではないようです。

file, _ := os.Open("/path/to/filename")
fileScanner := bufio.NewScanner(file)
lineCount := 0
for fileScanner.Scan() {
    lineCount++
}
fmt.Println("number of lines:", lineCount)

ファイルの行数を調べるためのより良い(より速く、より安価な)方法はありますか?

ベストアンサー1

bytes.Count改行文字を見つけるために使用する、より高速な行カウンターを次に示します。

行全体を返すために必要な余分なロジックとバッファリングをすべて取り除き、バイト スライス内の文字を検索するためにバイト パッケージによって提供されるアセンブリに最適化された関数を利用するため、処理が高速になります。

バッファを大きくすると、特にファイルが大きい場合に効果的です。私のシステムでは、テストに使用したファイルでは 32k バッファが最も高速でした。

func lineCounter(r io.Reader) (int, error) {
    buf := make([]byte, 32*1024)
    count := 0
    lineSep := []byte{'\n'}

    for {
        c, err := r.Read(buf)
        count += bytes.Count(buf[:c], lineSep)

        switch {
        case err == io.EOF:
            return count, nil

        case err != nil:
            return count, err
        }
    }
}

ベンチマーク出力:

BenchmarkBuffioScan   500      6408963 ns/op     4208 B/op    2 allocs/op
BenchmarkBytesCount   500      4323397 ns/op     8200 B/op    1 allocs/op
BenchmarkBytes32k     500      3650818 ns/op     65545 B/op   1 allocs/op

おすすめ記事