C++ ifstream:检查是否成功打开

C++ ifstream:检查是否成功打开,c++,iostream,C++,Iostream,一位同事刚刚告诉我,这个代码: std::ifstream stream(filename.c_str()); if (!stream) { throw std::runtime_error(".."); } 那就错了。他说,如果打开成功,ifstream的计算结果为0。我的代码可以正常工作,但我想找到文档,但没有看到其中说明了如何检查打开是否成功。你能给我指一下吗?接线员用于std::ifstream,因此您可以这样做 然而,在我看来,这是一种可怕的对操作员超载的滥用(由标准委员会)

一位同事刚刚告诉我,这个代码:

std::ifstream stream(filename.c_str());
if (!stream)
{
    throw std::runtime_error("..");
}
那就错了。他说,如果打开成功,
ifstream
的计算结果为0。我的代码可以正常工作,但我想找到文档,但没有看到其中说明了如何检查打开是否成功。你能给我指一下吗?

接线员用于
std::ifstream
,因此您可以这样做

然而,在我看来,这是一种可怕的对操作员超载的滥用(由标准委员会)。如果只执行
if(stream.fail())
,您也可以使用它来检查它是否有效,但是!是允许的(它不检查零,这是特殊的)

编辑:
只是出于兴趣-为什么不抛出异常?
是否只是在异常之前引入了流

还是我们进入了旧C++的事情——这只是一个异常,但它并不例外,

,你可以通过调用正确的位掩码来调用一个特定的流,从而在EOF/VAIL/BAD中的任何一个上引发异常。因此,您可以将上述初始问题中的示例改写为:

std::ifstream stream;
stream.exceptions(std::ios::failbit | std::ios::badbit);
stream.open(filename.c_str());
在这里,当设置failbit或badbit时,流将抛出异常。例如,如果失败,它将设置failbit并引发异常。当然,如果在流上设置了这些位中的任何一位,这将在以后引发异常,因此此重写与初始示例并不完全相同。你可以打电话

stream.exceptions(std::ios::goodbit);
取消流中的所有异常并返回检查错误。

您的同事错了。也许他忘了你不是在写C


代码很准确。这正是您应该检查流状态的方式。

不要忘记检查
stream.bad()
stream.good()
stream.fail()
,以及
stream.is\u open()
。唉……这个!重载以检查'fail'和'bad'。这里没有“滥用”。事实上,我认为fail比操作符更模糊和/或更容易混淆,只是因为它检查failbit和badbit,尽管它的名称不同。@abhinav:因为它(主要)是一个特殊的雪花-这(使用!表示“失败”)不是一个通用的模式,所以在我看来,它会降低易读性。20年来,我一直在想,一个不成功的ifstream对象的存在需要什么。。。可能再过20年,这个问题就可以解决了(通过引入另一个构造函数,使用另一个please\u throw()参数?)。希望此时,错误的原因将包含在exception对象中。