C++: std::istream 检查 EOF 而不读取/消耗令牌/使用运算符>>
我想测试 std::istream
是否已到达末尾而不从中读取。
我知道我可以这样检查 EOF:
if (is >> something)
但这有一系列问题。想象一下,有许多(可能是虚拟的)方法/函数期望 std::istream& 作为参数传递。 这意味着我必须做“家务”,检查每个变量中的 EOF,可能使用不同类型的 something
变量,或者创建一些奇怪的包装器来处理调用输入方法的场景。
我需要做的就是:
if (!IsEof(is)) Input(is);
方法IsEof
应该保证流的读取不会改变,这样上面的行就相当于:
Input(is)
对于Input
中读取的数据代码>方法。
如果没有通用的解决方案可以表示 std::istream ,是否有任何方法可以为 std::ifstream 或 cin 做到这一点>?
编辑: 换句话说,以下 assert
应始终通过:
while (!IsEof(is)) {
int something;
assert(is >> something);
}
I would like to test if a std::istream
has reached the end without reading from it.
I know that I can check for EOF like this:
if (is >> something)
but this has a series of problems. Imagine there are many, possibly virtual, methods/functions which expect std::istream&
passed as an argument.
This would mean I have to do the "housework" of checking for EOF in each of them, possibly with different type of something
variable, or create some weird wrapper which would handle the scenario of calling the input methods.
All I need to do is:
if (!IsEof(is)) Input(is);
the method IsEof
should guarantee that the stream is not changed for reading, so that the above line is equivalent to:
Input(is)
as regards the data read in the Input
method.
If there is no generic solution which would word for and std::istream
, is there any way to do this for std::ifstream
or cin
?
EDIT:
In other words, the following assert
should always pass:
while (!IsEof(is)) {
int something;
assert(is >> something);
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(5)
istream 类有一个 eof 位,可以使用
is.eof()
成员。编辑:所以您想查看下一个字符是否是 EOF 标记而不将其从流中删除?
if (is.peek() == EOF)
可能就是您想要的。请参阅 istream::peek 的文档The istream class has an eof bit that can be checked by using the
is.eof()
member.Edit: So you want to see if the next character is the EOF marker without removing it from the stream?
if (is.peek() == EOF)
is probably what you want then. See the documentation for istream::peek那是不可能的。 IsEof 函数如何知道您要读取的下一个项目是 int?
以下内容是否也不会触发任何断言?
也就是说,您可以使用
exceptions
方法将“内务管理”保留在一个地方。而不是
try
它不会阻止您在“为时已晚”之前阅读,但它确实避免了所有函数中都需要有 if(is >> x) if(is >> y) 等。
That's impossible. How is the
IsEof
function supposed to know that the next item you intend to read is an int?Should the following also not trigger any asserts?
That said, you can use the
exceptions
method to keep the "house-keeping' in one place.Instead of
try
It doesn't stop you from reading before it's "too late", but it does obviate the need to have if(is >> x) if(is >> y) etc. in all the functions.
一般情况下,
就足够了。还有 .good()、.bad()、.fail() 以获得更准确的信息
这是参考链接: http://www.cplusplus.com/reference/iostream/istream/
Normally,
is enough. There is also .good(), .bad(), .fail() for more exact information
Here is a reference link: http://www.cplusplus.com/reference/iostream/istream/
没有 isEof 函数是有充分理由的:很难以可用的方式指定。例如,运算符>>通常首先跳过空格(取决于标志),而其他一些输入函数可以读取空格。 isEof() 如何处理这种情况?是否从跳过空格开始?它是否取决于运算符使用的标志>>或不?它会恢复流中的空白吗?
我的建议是使用标准习惯用法并描述输入失败的特征,而不是尝试仅预测其原因之一:您仍然需要描述和处理其他原因。
There are good reasons for which there is no isEof function: it is hard to specify in an usable way. For instance, operator>> usually begin by skipping white spaces (depending on a flag) while some other input functions are able to read space. How would you isEof() handle the situation? Begin by skipping spaces or not? Would it depend on the flag used by operator>> or not? Would it restore the white spaces in the stream or not?
My advice is use the standard idiom and characterize input failure instead of trying to predict only one cause of them: you'd still need to characterize and handle the others.
不,一般情况下无法知道下一次读操作是否会到达 eof。
如果流连接到键盘,则 EOF 条件是我将在下一个提示时键入 Ctrl+Z/Ctrl+D。 IsEof(is) 如何检测到这一点?
No, in the general case there is no way of knowing if the next read operation will reach eof.
If the stream is connected to a keyboard, the EOF condition is that I will type Ctrl+Z/Ctrl+D at the next prompt. How would IsEof(is) detect that?