cin
cin的基本规则:接触到非空白字符(空格,制表,换行)即开始阅读,遇到空白字符即停止阅读。
istream.get()可以读取一个字符
cin.get():获取一个字符,包括空白字符。如果遇到结束符号,则返回-1。cin.get(char)读取一个字符,到指定字符中。cin.get(char*, int, char):读取到字符串/数组中,直到指定个数,或者遇到终止字符。
istream.getline(char*, int, char)可以读取一串字符
- 提取一行字符到字符串/数组中,直到指定个数,或遇到终止字符。
istream.peek()
- 观测下一个字符,指针并不后移。
istream.putback(char)
- 将一个字符添加到输入流中,下一个将会读到。
istream.ignore()
- 跳过n个字符,或者直到遇到了终结字符。
- 实质是修改流缓冲的指针:
basic_streambuf._Gnext。
cout
ostream.flush()
- 实质是清空缓冲流
ios._Mystrbuf
缓冲区
文件描述符是数字,是操作系统的概念。默认情况下,文件描述符 0, 1, 2都连接到终端 /dev/ptsx的。
stdin是一个文件指针,类型为 FILE*,也就是「流」,这是 C 语言的概念。默认情况下,stdin连接到进程的文件描述符 0,例如 /dev/tty/xxx。stdin和 stdout是有缓冲的,这个缓冲是用户区缓冲,是 C 语言提供的;而 stderr 没有缓冲。
cin 是 basic_istream类型的全局变量。
以下部分是猜想:cin连接到进程的文件描述符 0;C++ 为 cin 提供了缓冲,也就是所谓的流缓冲。
为什么不要混用 cout 和 printf,因为两者使用不同的缓冲机制;听说 C++ 会将自身的流缓冲和 C 的输出缓冲区同步。
注:cerr是无缓冲的。
为什么需要缓冲区:因为 write()是系统调用,消耗比较大(涉及到从用户态到内核态的切换),减少调用次数可以提高效率。
参考:https://stackoverflow.com/questions/21084218/difference-between-write-and-printf
格式控制
格式控制的两种方式
- 通过具体的参数
- 通过方法设置参数:
cout.width(int) - 通过操作器设置参数:
cout << setw(int)
- 通过方法设置参数:
- 通过设置
flags- 通过方法设置
flags:cout.setf(ios::fmtflags) - 通过有参数操作器设置
flags:cout << setiosflags(ios::fmtflags) - 通过无参数操作器设置
flags:cout << flags_funcPtr。
- 通过方法设置
通过格式标志控制格式
常用的标志有:
| 标志 | 说明 |
|---|---|
boolalpha, noboolalpha |
布尔值显示为true还是 1 |
oct, dec, hex |
显示进制 |
left, right |
对齐方式,需要以显示宽度为前提 |
scientific |
科学计数法形式输出浮点数 |
fixed |
以普通小数形式显示浮点数 |
showpos, noshowpos |
非负值显示+ |
skipws, noskipws |
输入时跳过空白字符 |
uppercase, nouppercase |
十六进制,科学计数法的字符大/小写 |
设置参数控制格式
// 设置显示宽度,超出会截断,不足以空白填充cout << setw(int);cout.width(int);// 设置填充字符cout << setfill(char);cout.fill(char);// 设置浮点数的显示精度cout << setprecision(int);cout.precision(int);// 设置整数显示的进制cout << setbase(int);
