测试 iStream 对象

testing an istream object

提问人:Aminos 提问时间:8/9/2016 更新时间:8/9/2016 访问量:3115

问:

当我在测试中使用 std::istream 对象(在下面的示例中来自 cplusplus.com,一个 std::ifstream)时:“if (myistreamobject)”,在堆栈中自动分配的对象永远不会为 null,对?...在下面的示例中,我们使用相同的测试来检查是否从文件中读取了所有字节...这真的是一个奇怪的代码,我通常在处理指针时使用这种风格......

我想知道 std::istream 中使用哪种机制在测试中返回一个值,以及该值的真正含义......(上次操作的成功/失败??它是布尔强制转换的重载(如 MFC 类 CString 中的 const char* 运算符强制转换)还是另一种技术?

因为对象从来都不是 null,所以把它放在测试中将始终返回 true。

// read a file into memory
#include <iostream>     // std::cout
#include <fstream>      // std::ifstream

int main () {

  std::ifstream is ("test.txt", std::ifstream::binary);
  if (is) {
    // get length of file:
    is.seekg (0, is.end);
    int length = is.tellg();
    is.seekg (0, is.beg);

    char * buffer = new char [length];

    std::cout << "Reading " << length << " characters... ";
    // read data as a block:
    is.read (buffer,length);

    if (is) // <== this is really odd
      std::cout << "all characters read successfully.";
    else
      std::cout << "error: only " << is.gcount() << " could be read";
    is.close();

    // ...buffer contains the entire file...

    delete[] buffer;
  }
  return 0;
}
C++ IOstream istream

评论

1赞 πάντα ῥεῖ 8/9/2016
请在这里阅读: en.cppreference.com/w/cpp/io/basic_ios/operator_bool

答:

4赞 kfsone 8/9/2016 #1
if (expression)

它评估的测试是布尔值。它适用于指针,因为 // 计算为 ,以及其他所有内容。出于同样的原因,它适用于整数值。expressiontruenullptrNULL0falsetrue

对于对象,它属于 ,请参阅 http://en.cppreference.com/w/cpp/io/basic_ios/operator_booloperator bool()

检查流是否没有错误。

1) 如果 fail() 返回 true,则返回 null 指针,否则返回非 null 指针。此指针可隐式转换为布尔值,并可用于布尔上下文。

2) 如果流没有错误并且已准备好进行 I/O 操作,则返回 true。具体来说,返回 !fail()。

此运算符可以使用返回对流的引用的流和函数作为循环条件,从而产生惯用的C++输入循环,例如 while(stream >> value) {...} 或 while(getline(stream, string)){...}。

仅当输入操作成功时,此类循环才会执行循环的正文。

2赞 Inline 8/9/2016 #2

std::istream运营商声明了以下权利:explicit operator bool() const;

当你写真的是调用不检查非零时if(SomeStdIstremObject) { ... }if(SomeStdIstreamObject.operator bool())

3赞 BiagioF 8/9/2016 #3

operator bool() 

如果流没有错误,则返回 true,否则返回 false。

无错误”概念与之前在流本身上执行的操作有关。

例如:调用构造函数后

std::ifstream is ("test.txt", std::ifstream::binary);

在流对象中设置内部状态标志。因此,当您调用运算符 bool 时,您可以检查构造操作是否失败。

此外,该方法

is.read(...)

此外,请设置此内部状态标志,如参考中所示:

通过修改内部状态标志来发出错误信号:eofbitfailbit、badbit

因此,在方法调用之后,如果流到达 EOF(文件末尾),则设置状态位,运算符 bool 将返回一个正值。

这意味着在这种情况下,当您使用

if (is) { ... }

并设置状态位,则验证条件并取 if 分支。