基础IO流
C++的IO以面向对象的形式实现, 同时兼容了C语言面向过程的IO方式
C++ 标准库提供了四个基本流对象:
cin:用于从标准输入(通常是键盘)读取数据。
cout:用于向标准输出(通常是控制台)写入数据。
cerr:用于向标准错误输出写入数据,通常用于报告错误。
clog:用于向标准日志输出写入数据,通常用于记录日志信息。
- C++中可以通过重载流插入和流提取(std::istream、std::ostream)操作符更好的支持自定义对象的输入输出
如下:
string str;
while(cin >> str){}
上述该种方式输入时, 首先是因为string重载了>>
操作符, 调用了istream& operator >> (istream& is, string& str)
重载函数, 然后返回值调用了operator bool()
将自定义类型转换成对应的true或者false(bool类型)进行判断.
结束该进程时, 可以通过Ctrl + C
直接杀死进程, 或者Ctrl + Z + 换行
表示读取到了结尾即退出循环
-
tips1: 将自定义类型转换为内置类型时, 可以通过重载对应的
explicit operator 类型(){}
函数来实现, 如operator int(){return _a}//无显式写出返回值,但是要返回对应类型的变量
,内置类型转换为自定义类型时, 则是通过自定义类型对应的构造函数实现. -
tips2: 自定义类型实现的流插入和流提取可以提供给cout/cin, ifstream/ofstream等类型的流提取和流插入函数实现多态使用, 可更方便的构造自定义类型.如
Date date; cin >> date; //或者是如下 ifstream ifs("date.txt");//默认打开方式是文本读的方式 ifs >> date;//可直接读入该date对象中
-
二进制读写: 在内存中是如何存储则如何写到磁盘文件(以如下模式打开文件流:ios_base::in | ios_base::binary)
- 优点: 读写效率高
- 缺点
- 写出的内容无法读懂
- 对于需要深浅拷贝的自定义类型无法正确拷贝(地址会改变)
-
文本读写: 对象数据序列化字符串写出, 读回时也是字符串, 即由二进制序列, 反序列化转成对象数据(即将字符串转为对应数据)
(以字符串方式读写)- 优点: 能够读懂写出的内容
- 缺点: 存在转换过程, 效率较慢
-
上述读写方式当要进行自定义类型的读写时, 只要自定义类型重写了流插入和流提取操作符, 都可直接使用流插入和流提取进行操作
即可以直接如下方式操作进行写入文件(同cout和cin的使用一样, 默认以空格或换行分割)
Date date; ofstream ofs("date.txt"); ofs << date;
文件流
C++ 提供了 std::fstream、std::ifstream 和 std::ofstream 类来支持文件 IO。
std::fstream:同时支持读写文件。
std::ifstream:只支持从文件读取数据。
std::ofstream:只支持将数据写入文件。
#include <fstream>
#include <iostream>
int main() {
std::ofstream outfile("example.txt");
if (!outfile) {
std::cerr << "Error opening file for writing!" << std::endl;
return 1;
}
outfile << "Hello, world!" << std::endl;
outfile.close();
std::ifstream infile("example.txt");
if (!infile) {
std::cerr << "Error opening file for reading!" << std::endl;
return 1;
}
std::string line;
while (std::getline(infile, line)) {
std::cout << line << std::endl;
}
infile.close();
return 0;
}
字符流
C++ 提供了 std::stringstream、std::istringstream 和 std::ostringstream 类来支持字符串 IO。
std::stringstream:同时支持从字符串读取和写入数据。
std::istringstream:只支持从字符串读取数据。
std::ostringstream:只支持将数据写入字符串。
#include <sstream>
#include <iostream>
int main() {
std::string input = "123 456 789";
std::istringstream iss(input);
int num;
while (iss >> num) {
std::cout << num << std::endl;
}
std::ostringstream oss;
oss << "The sum is " << (123 + 456 + 789);
std::cout << oss.str() << std::endl;
return 0;
}
格式化输出
C++ 提供了各种流操纵符(如 std::setw、std::setprecision、std::left、std::right 等)来格式化输出
一般不常用,还是使用printf吧
#include <iostream>
#include <iomanip> // 包含流操纵符
int main() {
double pi = 3.141592653589793;
std::cout << std::fixed << std::setprecision(2) << pi << std::endl; // 输出两位小数的π
std::cout << std::setw(10) << std::left << "Hello" << std::endl; // 左对齐并设置字段宽度为10
std::cout << std::setw(10) << std::right << "World" << std::endl; // 右对齐并设置字段宽度为10
return 0;
}