eof位:读取失败之前或之后?

Vin*_*ent 3 c++ io stream ifstream eof

我目前正在为一些IO操作编写一个类.某些函数返回IO操作是否成功.如果我正在读取文件,我想知道是否应该返回std::ifstream::good()!std::ifstream::fail()指示IO操作是否成功.

差异来自于这eof一点,我不确定我是否正确理解它.

假设我有一个包含4个字节的二进制文件(1个整数).

假设我读了这个整数.

我的问题是:eof在此操作之后或下一次IO操作之后将设置标志(将失败)?

如果在此操作之后直接设置,如果我的读取函数返回std::ifstream::good(),则结果将是false(但是正确读取了整数).

你可以在设置eof位时向我解释一下,在我的函数结束时应该返回什么?

Ker*_* SB 5

该EOF标志设置后,尝试读取过流的末尾.

你的函数应该返回对原始流的引用,你应该在循环或条件中使用它,如下所示:

std::istream & process(std::istream & is)
{
    int n;
    if (is >> n) { std::cout << "Read one int: " << n << "\n"; }
    return is;
}

int main()
{
    std::ifstread infile("data.bin");

    while (process(infile)) { }
}
Run Code Online (Sandbox Code Playgroud)


CB *_*ley 5

当读取操作尝试读取超出流的末尾时,设置流的"eof"位.读取超出流末尾的读取操作可能成功也可能不成功.这与"eof"位是否设置无关.

因此,您应始终检查读取操作本身的结果,而不是在读取后检查流标志的状态.

有关所有四种组合的示例:

#include <iostream>
#include <istream>

int main()
{
        int n;
        if (std::cin >> n)
                std::cout << "read an int with value = " << n << '\n';
        else
                std::cout << "read of int failed\n";

        std::cout << "cin.eof() = " << std::cin.eof() << '\n';
        return 0;
}
Run Code Online (Sandbox Code Playgroud)

成功读取设置eof位:

$ printf 1 | ./a.out
read an int with value = 1
cin.eof() = 1
Run Code Online (Sandbox Code Playgroud)

成功读取未设置eof位:

$ echo 1 | ./a.out
read an int with value = 1
cin.eof() = 0
Run Code Online (Sandbox Code Playgroud)

不设置eof位的不成功读取:

$ printf abc | ./a.out
read of int failed
cin.eof() = 0
Run Code Online (Sandbox Code Playgroud)

设置eof位的不成功读取:

$ echo | ./a.out
read of int failed
cin.eof() = 1
Run Code Online (Sandbox Code Playgroud)