cin
cin >> 如何检查输入
不同版本的抽取运算符查看输入流的方法是相同的. 他们跳过空白(空格, 换行符, 制表符), 直到遇到非空白字符. 但对于c语言的字符输入函数, 并不是这样的, 在单字符模式下(char, unsigned char或signed char), >> 运算符将读取该字符, 将它放置到指定的位置. 在其他模式下, >> 运算符将读取一个指定类型的数据. 也就是说, 它读取从非空白字符开始, 到与目标类型不匹配的第一个字符之间的全部内容. 来看一个例子:
char philosophy[20];
int distance;
char initial;
cin >> philosophy >> distance >> initial;
对于上面的代码, 我们输入一下内容:
stoic 100 Blaise
实际上对应的结果为:
philosophy: stoic
distance: 100
initial: B
剩下的laise将留在输入流中, 下一个cin语句将从这里开始读取.
输入有时可能没有满足程序的期望, 例如:
int ele;
cin >> ele;
如果我们输入的是asdf, 在这种情况下, 抽取运算符将不会修改ele的值, 并返回0(如果istream对象的错误状态被设置, if或while语句将判定该对象为false). 返回值false让程序能够检查输入是否满足要求, 来看一个例子:
// check_input.cpp
#include <iostream>
int main()
{
using namespace std;
cout << "Enter numbers: ";
int sum = 0;
int input;
while(cin >> input)
{
sum += input;
cout << "input 1 = " << input << endl;
}
cout << "Last value entered = " << input << endl;
cout << "Sum = " << sum << endl;
return 0;
}
来看一下运行结果:
由于输入被缓存, 因此第二行输入在用户按下回车键之前, 是不会发送给程序的, 然而由于有个非法字符z不与任何一种格式匹配上, 所以输入与预期格式不匹配, 因此表达式cin >> input的结果为false, 因此while循环终止.
流状态:
cin, cout对象包含一个描述流状态(stream state)的数据成员(从ios_base类那里继承的). 流状态(被定义为iostate类型, 而iostate是一种bitmask类型)由三个ios_base元素组成: eofbit, badbit, failbit, 其中每个元素都是1位, 可以是1(设置)或0(清除). 当cin操作到达文件末尾时, 它将设置eofbit; 当cin操作未能读取到预期的字符时, 它将设置failbit; I/O失败(试图读取不可访问的文件或试图写入写保护的磁盘), 也可能将failbit设置为1. 在一些无法诊断的失败破坏流时, badbit元素将被设置. 当全部三个状态位都设置为0时, 说明一切顺利, 程序可以检查流状态, 并使用这些信息来决定下一步做什么.
下面是一些流状态的方法和位信息:
eofbit: 如果达到文件末尾, 则设置为1
badbit: 如果流被破坏, 则设置为1, 例如: 文件读取错误
failbit: 如果输入操作需哦未能读取预期的字符或输出操作没有写入预期的字符, 则设置为1
goodbit: 另一种表示0的方法.
good(): 如果流可以使用(所有的为都被清除), 则返回true
eof(): 如果eofbit被设置, 则返回true
bad(): 如果badbit被设置, 则返回true
fail(): 如果badbit或failbit被设置, 则返回true
rdstate(): 返回流状态.
exceptions(): 返回一个位掩码, 指出哪些标记导致异常被引发.
exceptions(iosstate ex): 设置哪些状态将导致clear()引发异常, 例如: 如果ex是eofbit, 则如果eofbit被设置, clear()将引发异常
clear(iostate s): 流状态设置为s: s默认值为0(goodbit), 如果(restate() & exceptions()) != 0 , 则引发异常basic_ios::failure
setstate(iostate s): 调用clear(rdstate() | s). 这将设置与s中设置的位对应的流状态位, 其他流状态位保持不变.
设置状态
clear()和setstate()很相似, 他们都重置状态, 但采取的方式不同, clear()方法将状态设置为它的参数