Go 中逐行读取文件
我无法在 Go 中找到 file.ReadLine
函数。
如何逐行读取文件?
I'm unable to find file.ReadLine
function in Go.
How does one read a file line by line?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(13)
在 Go 1.1 及更新版本中,最简单的方法是使用
bufio.Scanner
。这是一个从文件中读取行的简单示例:这是从
Reader
逐行读取的最干净的方法。有一个警告:扫描仪将在行长度超过 65536 个字符时出错。如果您知道行长度大于 64K,请使用
Buffer()
增加扫描仪容量的方法:In Go 1.1 and newer the most simple way to do this is with a
bufio.Scanner
. Here is a simple example that reads lines from a file:This is the cleanest way to read from a
Reader
line by line.There is one caveat: Scanner will error with lines longer than 65536 characters. If you know your line length is greater than 64K, use the
Buffer()
method to increase the scanner's capacity:注意:在 Go 的早期版本中,接受的答案是正确的。 查看得票最高的答案包含实现此目的的最新惯用方法。
有函数ReadLine 位于包
bufio
中。请注意,如果该行不适合读取缓冲区,该函数将返回不完整的行。如果您希望始终通过一次调用函数来读取程序中的整行,则需要将 ReadLine 函数封装到您自己的函数中,该函数在以下位置调用 ReadLine for 循环。
bufio.ReadString('\n')
并不完全等同于ReadLine
,因为ReadString
无法处理最后一行为文件不以换行符结尾。NOTE: The accepted answer was correct in early versions of Go. See the highest voted answer contains the more recent idiomatic way to achieve this.
There is function ReadLine in package
bufio
.Please note that if the line does not fit into the read buffer, the function will return an incomplete line. If you want to always read a whole line in your program by a single call to a function, you will need to encapsulate the
ReadLine
function into your own function which callsReadLine
in a for-loop.bufio.ReadString('\n')
isn't fully equivalent toReadLine
becauseReadString
is unable to handle the case when the last line of a file does not end with the newline character.编辑:从 go1.1 开始,惯用的解决方案是使用 bufio.Scanner
我写的一种轻松读取文件中每一行的方法。 Readln(*bufio.Reader) 函数从底层 bufio.Reader 结构返回一行(无 \n)。
您可以使用 Readln 读取文件中的每一行。以下代码读取文件中的每一行并将每一行输出到 stdout。
干杯!
EDIT: As of go1.1, the idiomatic solution is to use bufio.Scanner
I wrote up a way to easily read each line from a file. The Readln(*bufio.Reader) function returns a line (sans \n) from the underlying bufio.Reader struct.
You can use Readln to read every line from a file. The following code reads every line in a file and outputs each line to stdout.
Cheers!
有两种常见的逐行读取文件的方法。
在我的测试用例中,~250MB,~2,500,000 行,bufio.Scanner(使用时间:0.395491384s)比 bufio.Reader 更快.ReadString(使用时间:0.446867622s)。
源代码: https://github.com/xpzouying/go-practice/tree/ master/read_file_line_by_line
读取文件使用 bufio.Scanner,
读取文件使用 bufio.Reader,
There two common way to read file line by line.
In my testcase, ~250MB, ~2,500,000 lines, bufio.Scanner(time used: 0.395491384s) is faster than bufio.Reader.ReadString(time_used: 0.446867622s).
Source code: https://github.com/xpzouying/go-practice/tree/master/read_file_line_by_line
Read file use bufio.Scanner,
Read file use bufio.Reader,
来自此 gist 的示例,
但是当存在大于扫描仪缓冲区的行时,这会产生错误。
发生这种情况时,我所做的是使用
reader := bufio.NewReader(inFile)
创建并连接我自己的缓冲区,或者使用ch, err := reader.ReadByte()
或len, err := reader.Read(myBuffer)
我使用的另一种方法(用上面的文件替换 os.Stdin),当行很长(isPrefix)并且忽略空行:
Example from this gist
but this gives an error when there is a line that larger than Scanner's buffer.
When that happened, what I do is use
reader := bufio.NewReader(inFile)
create and concat my own buffer either usingch, err := reader.ReadByte()
orlen, err := reader.Read(myBuffer)
Another way that I use (replace os.Stdin with file like above), this one concats when lines are long (isPrefix) and ignores empty lines:
您还可以使用带有 \n 作为分隔符的 ReadString:
You can also use ReadString with \n as a separator:
另一种方法是使用 io/ioutil 和 strings 库读取整个文件的字节,将它们转换为字符串并使用“
\n< /code>”(换行符)字符作为分隔符,例如:
从技术上讲,您不是逐行读取文件,但是您可以使用此技术解析每一行。此方法适用于较小的文件。如果您尝试解析大型文件,请使用逐行读取的技术之一。
Another method is to use the
io/ioutil
andstrings
libraries to read the entire file's bytes, convert them into a string and split them using a "\n
" (newline) character as the delimiter, for example:Technically you're not reading the file line-by-line, however you are able to parse each line using this technique. This method is applicable to smaller files. If you're attempting to parse a massive file use one of the techniques that reads line-by-line.
bufio.Reader.ReadLine() 效果很好。但如果你想通过字符串读取每一行,请尝试使用 ReadString('\n') 。它不需要重新发明轮子。
bufio.Reader.ReadLine() works well. But if you want to read each line by a string, try to use ReadString('\n'). It doesn't need to reinvent the wheel.
在下面的代码中,我从 CLI 读取兴趣,直到用户按 Enter 键并且我正在使用 Readline:
In the code bellow, I read the interests from the CLI until the user hits enter and I'm using Readline:
这是一个函数
ReadFromStdin()
的示例,它类似于fmt.Scan(&name)
但它接受所有带空格的字符串,例如:“Hello My Name Is .. ”。Here is an example with function
ReadFromStdin()
it's likefmt.Scan(&name)
but its takes all strings with blank spaces like: "Hello My Name Is ..."扫描*功能在这里非常有用。这是 单词扫描器示例 的稍微修改版本,来自 go-lang 文档扫描文件中的行。
The Scan* functions are of great user here. Here is a slightly modified version of word scanner example from go-lang docs to scan lines from a file.
在新版本的Go 1.16中,我们可以使用包embed来读取文件内容,如下所示。
有关更多详细信息,请访问 https://tip.golang.org/pkg/embed/
和
https://golangtutorial.dev/tips/embed-files-in-go/< /a>
In the new version of Go 1.16 we can use package embed to read the file contents as shown below.
For more details go through https://tip.golang.org/pkg/embed/
And
https://golangtutorial.dev/tips/embed-files-in-go/