如何在从文件中读取时查找EOF

时间:2013-01-22 22:49:15

标签: go file-handling

我使用以下代码在Go中读取文件:

spoon , err := ioutil.ReadFile(os.Args[1])
if err!=nil {
        panic ("File reading error")
}

现在我检查我选择的每个字节是什么字符。例如:

spoon[i]==' ' //for checking space

同样我读了整个文件(我知道还有其他方法可以阅读) 但保持这种方式完好无损,我怎么知道我已达到文件的EOF而我应该再停止阅读呢?

请不要建议找到spoon的长度并开始循环。我想找一个找到EOF的确定方法。

5 个答案:

答案 0 :(得分:16)

使用io.EOF测试文件结尾。例如,要计算文件中的空格:

package main

import (
    "fmt"
    "io"
    "os"
)

func main() {
    if len(os.Args) <= 1 {
        fmt.Println("Missing file name argument")
        return
    }
    f, err := os.Open(os.Args[1])
    if err != nil {
        fmt.Println(err)
        return
    }
    defer f.Close()
    data := make([]byte, 100)
    spaces := 0
    for {
        data = data[:cap(data)]
        n, err := f.Read(data)
        if err != nil {
            if err == io.EOF {
                break
            }
            fmt.Println(err)
            return
        }
        data = data[:n]
        for _, b := range data {
            if b == ' ' {
                spaces++
            }
        }
    }
    fmt.Println(spaces)
}

答案 1 :(得分:7)

ioutil.ReadFile()将文件的全部内容读入字节切片。你不需要关心EOF。 EOF是一次读取一个文件块时所需的构造。当您一次读取一个块时,您需要知道哪个块已到达文件的末尾。

ioutil.ReadFile()返回的字节切片的长度就是您所需要的。

data := ioutil.ReadFile(os.Args[1])

// Do we need to know the data size?
slice_size := len(data)

// Do we need to look at each byte?
for _,byte := range data {
    // do something with each byte
}

答案 2 :(得分:3)

当你使用ioutil.ReadFile()时,你根本没有看到io.EOF,因为ReadFile将读取整个文件,直到达到EOF。因此返回的切片整个文件。来自doc:

  

ReadFile读取由filename命名的文件并返回内容。成功的调用返回err == nil,而不是err == EOF。因为ReadFile读取整个文件,所以它不会将来自Read的EOF视为要报告的错误。

从您的问题中,您明确提到您知道还有其他方法可以读取该文件,其中一些方法要求您测试io.EOF的错误,而不是ReadFile。

然后,使用您拥有的切片,您可以使用for ... range构造读取文件,正如其他人所提到的那样。这是一种肯定的方式来读取整个文件而已(仅次于ReadFile负责)。或者从0迭代到len(勺子) - 1也可以工作,但范围更惯用,基本上也是一样。

换句话说:当你到达切片的末尾时,你到达文件的末尾(如果ReadFile没有返回错误)。

答案 3 :(得分:2)

切片没有文件结尾的概念。 ioutil.ReadFile返回的切片具有特定长度,该长度反映了从中读取的文件的大小。一个常见的习惯用法,但在这种情况下只能使用一个,就是对切片进行测距,有效地“消耗”最初位于文件中的所有字节:

for i, b := range spoon {
        // At index 'i' is byte 'b'
        // At file's offset 'i', 'b' was read
        ... do something useful here
}

答案 4 :(得分:0)

这是您需要查找的有关文件结尾 (EOF) 的内容

if err != nil {
        if errors.Is(err, io.EOF) { // prefered way by GoLang doc
            fmt.Println("Reading file finished...")
        }
        break
    }