# `std::basic_istream`总结
std::basic_istream
总结
文章目录
- `std::basic_istream`总结
- 概述
- 常用类型定义
- 全局对象
- 核心成员函数
- 1. 格式化输入
- 2. 非格式化输入
- 3. 流定位
- 4. 其他功能
- 继承的功能
- 来自 `std::basic_ios`
- 状态检查
- 状态管理
- 来自 `std::ios_base`
- 格式化标志
- 流打开模式
- 特点说明
- 例子
- `std::basic_istream`全面用法演示
- 1. 基础用法(格式化输入)
- 2. 非格式化输入操作
- 3. 流状态管理
- 4. 定位操作
- 5. 高级用法(sentry类)
- 6. 综合示例(文件处理)
概述
std::basic_istream
是 C++ 标准库中用于高级字符流输入操作的类模板,定义于 <istream>
头文件中。它提供格式化和非格式化输入功能,构建在 basic_streambuf
接口之上。
常用类型定义
类型 | 定义 |
---|---|
std::istream | std::basic_istream<char> |
std::wistream | std::basic_istream<wchar_t> |
全局对象
对象 | 描述 |
---|---|
cin | 标准 C 输入流 (stdin ) |
wcin | 宽字符标准输入流 |
核心成员函数
1. 格式化输入
- **
operator>>
**: 提取格式化数据(如整数、字符串等)
2. 非格式化输入
函数 | 描述 |
---|---|
get | 提取字符 |
peek | 读取下一个字符但不提取 |
unget | 将字符放回输入流 |
putback | 将字符放回输入流 |
getline | 提取字符直到遇到指定分隔符 |
ignore | 提取并丢弃字符直到遇到指定字符 |
read | 提取字符块 |
readsome | 提取当前可用的字符块 |
gcount | 返回最后非格式化输入提取的字符数 |
3. 流定位
函数 | 描述 |
---|---|
tellg | 返回输入位置指示器 |
seekg | 设置输入位置指示器 |
4. 其他功能
-
**
sync
**: 与底层存储设备同步 -
**
swap
** (C++11): 交换流对象(除关联缓冲区外)
继承的功能
来自 std::basic_ios
状态检查
函数 | 描述 |
---|---|
good() | 检查是否无错误 |
eof() | 检查是否到达文件末尾 |
fail() | 检查是否发生错误 |
bad() | 检查是否发生不可恢复错误 |
operator! | 错误检查(fail() 的同义词) |
operator bool | 无错误检查(!fail() 的同义词) |
状态管理
-
rdstate()
: 返回状态标志 -
setstate()
: 设置状态标志 -
clear()
: 修改状态标志
来自 std::ios_base
格式化标志
标志 | 描述 |
---|---|
dec | 十进制整数 I/O |
oct | 八进制整数 I/O |
hex | 十六进制整数 I/O |
left | 左对齐输出 |
right | 右对齐输出 |
scientific | 科学计数法浮点输出 |
fixed | 固定点表示法浮点输出 |
boolalpha | 布尔值字母格式输入输出 |
流打开模式
模式 | 描述 |
---|---|
in | 打开用于读取 |
out | 打开用于写入 |
binary | 二进制模式打开 |
ate | 打开后立即定位到文件末尾 |
app | 每次写入前定位到文件末尾 |
trunc | 打开时清空内容 |
特点说明
-
主要用于处理字符流的高级别输入操作
-
同时支持格式化和非格式化输入
-
通过虚继承从
std::basic_ios
派生 -
通常唯一非继承的数据成员是
gcount()
的返回值 -
提供 sentry 类用于输入操作前的准备工作
此总结涵盖了 std::basic_istream
的主要功能和特性,适用于日常使用参考。
例子
std::basic_istream
全面用法演示
我将全面展示 std::basic_istream
的核心功能,包括格式化输入、非格式化输入、流状态管理、定位操作、自定义sentry类等高级用法。
1. 基础用法(格式化输入)
#include <iostream>
#include <sstream>
#include <iomanip>void basic_usage() {// 1. 基本格式化输入std::basic_istringstream<char> iss1("42 3.14 Hello");int i; double d; std::string s;iss1 >> i >> d >> s;std::cout << "Int: " << i << ", Double: " << d << ", String: " << s << "\n";// 2. 控制输入格式std::basic_istringstream<char> iss2("0x2A 0101");iss2 >> std::hex >> i; // 十六进制输入std::cout << "Hex: " << i << "\n";iss2 >> std::oct >> i; // 八进制输入std::cout << "Oct: " << i << "\n";// 3. 设置输入字段宽度std::basic_istringstream<char> iss3("123456");char buf[4];iss3 >> std::setw(4) >> buf;std::cout << "Width-limited: " << buf << "\n";
}
2. 非格式化输入操作
#include <iostream>
#include <sstream>void unformatted_input() {std::basic_istringstream<char> iss("ABCDEFGHIJ\n123456");// 1. get() 系列方法char c1, c2, c3;iss.get(c1).get(c2);std::cout << "Got: " << c1 << c2 << "\n";// 2. getline() 方法char line[10];iss.getline(line, sizeof(line));std::cout << "Line: " << line << "\n";// 3. read() 方法char buffer[5];iss.read(buffer, 4);buffer[4] = '\0';std::cout << "Read: " << buffer << "\n";// 4. peek() 和 putback()c3 = iss.peek();std::cout << "Peek: " << c3 << "\n";iss.putback('X');iss.get(c3);std::cout << "After putback: " << c3 << "\n";// 5. ignore() 方法iss.ignore(2, '5'); // 跳过2个字符或直到遇到'5'iss.get(c3);std::cout << "After ignore: " << c3 << "\n";// 6. gcount() 获取最后读取的字符数std::cout << "Last read count: " << iss.gcount() << "\n";
}
3. 流状态管理
#include <iostream>
#include <sstream>void stream_state() {std::basic_istringstream<char> iss("123 abc 456");// 1. 基本状态检查int val;iss >> val;if (iss.good()) {std::cout << "Good state: " << val << "\n";}// 2. 处理失败状态iss >> val; // 尝试读取非数字if (iss.fail()) {std::cout << "Failed to read\n";iss.clear(); // 清除错误状态}// 3. 处理eof状态std::string str;while (iss >> str) {std::cout << "Read: " << str << "\n";}if (iss.eof()) {std::cout << "Reached EOF\n";}// 4. 综合状态检查iss.clear();iss.setstate(std::ios_base::badbit);if (iss.bad()) {std::cout << "Bad bit set\n";}
}
4. 定位操作
#include <iostream>
#include <sstream>void positioning() {std::basic_istringstream<char> iss("0123456789ABCDEF");// 1. tellg() 获取当前位置auto pos = iss.tellg();std::cout << "Start pos: " << pos << "\n";// 2. seekg() 绝对定位iss.seekg(5);char c;iss.get(c);std::cout << "Char at pos 5: " << c << "\n";// 3. seekg() 相对定位iss.seekg(2, std::ios_base::cur);iss.get(c);std::cout << "Char at pos+2: " << c << "\n";// 4. seekg() 从末尾定位iss.seekg(-3, std::ios_base::end);iss.get(c);std::cout << "Char 3 from end: " << c << "\n";// 5. 保存和恢复位置auto save_pos = iss.tellg();iss.seekg(0);iss.get(c);std::cout << "First char: " << c << "\n";iss.seekg(save_pos);iss.get(c);std::cout << "Restored char: " << c << "\n";
}
5. 高级用法(sentry类)
#include <iostream>
#include <sstream>void advanced_usage() {std::basic_istringstream<char> iss(" Hello World");// 1. 手动使用sentrystd::basic_istream<char>::sentry se(iss);if (se) {char c;iss.get(c);std::cout << "First non-whitespace: " << c << "\n";}// 2. 在自定义提取操作中使用sentrystruct Point { int x, y; };std::basic_istringstream<char> iss2("(10,20)");char dummy;Point p;iss2 >> dummy; // 读取'('if (dummy != '(') iss2.setstate(std::ios_base::failbit);std::basic_istream<char>::sentry se2(iss2);if (se2) {iss2 >> p.x >> dummy >> p.y;if (dummy != ',') iss2.setstate(std::ios_base::failbit);}iss2 >> dummy; // 读取')'if (dummy != ')') iss2.setstate(std::ios_base::failbit);if (iss2) {std::cout << "Point: (" << p.x << "," << p.y << ")\n";}
}
6. 综合示例(文件处理)
#include <iostream>
#include <fstream>
#include <vector>void file_processing() {// 1. 创建测试文件{std::basic_ofstream<char> ofs("test.txt");ofs << "10 20 30\n40 50 60\n70 80 90\n";}// 2. 读取文件内容std::basic_ifstream<char> ifs("test.txt");if (!ifs) {std::cout << "Failed to open file\n";return;}std::vector<int> values;int val;// 3. 读取直到EOFwhile (ifs >> val) {values.push_back(val);// 检查流状态if (ifs.bad()) {std::cout << "Critical error\n";break;}if (ifs.fail()) {ifs.clear();ifs.ignore(1); // 跳过错误字符}}// 4. 输出结果std::cout << "Read values:";for (int v : values) {std::cout << " " << v;}std::cout << "\n";// 5. 重新定位并读取ifs.clear();ifs.seekg(0);std::string line;while (std::getline(ifs, line)) {std::cout << "Line: " << line << "\n";}
}int main() {basic_usage();unformatted_input();stream_state();positioning();advanced_usage();file_processing();return 0;
}
这个全面演示涵盖了:
-
所有主要的格式化输入操作
-
完整的非格式化输入方法
-
详细的流状态管理
-
全面的定位操作
-
高级sentry类用法
-
实际文件处理示例
每个示例都直接使用basic_istream及其相关组件,展示了从基础到高级的各种用法场景。