当前位置: 首页 > ds >正文

c++文件操作详解

C++ 提供了强大的文件操作功能,主要通过 <fstream> 头文件中的类来实现。以下是对C++文件操作的全面解析:

一、文件流类体系

C++ 文件操作基于流的概念,核心类包括:

类名描述继承自
fstream文件流(读写操作)iostream
ifstream输入文件流(读操作)istream
ofstream输出文件流(写操作)ostream
filebuf文件缓冲区streambuf

二、文件打开模式

文件打开模式通过位掩码常量指定,可组合使用:

模式标志描述
ios::in打开文件进行读取(ifstream默认)
ios::out打开文件进行写入(ofstream默认),会截断现有文件
ios::app追加模式,所有写入操作都在文件末尾进行
ios::ate打开文件后定位到文件末尾
ios::trunc如果文件存在,则截断文件(out模式默认启用)
ios::binary以二进制模式打开文件(避免文本转换)
ios::nocreate如果文件不存在,打开失败(非标准,建议用C++17文件系统)
ios::noreplace如果文件存在,打开失败(非标准)

三、文件基本操作

1. 打开文件

#include <fstream>// 方式1:构造函数打开
std::ofstream outFile("output.txt", std::ios::out | std::ios::app);// 方式2:open()方法打开
std::ifstream inFile;
inFile.open("input.txt", std::ios::in);// 检查文件是否成功打开
if (!outFile.is_open()) {std::cerr << "Error opening file!" << std::endl;return 1;
}

2. 关闭文件

outFile.close();  // 显式关闭文件
inFile.close();   // 文件流析构时会自动关闭,但显式关闭是好习惯

3. 文件状态检查

if (inFile.fail()) {// 操作失败(如类型不匹配)
}if (inFile.bad()) {// 严重错误(如磁盘故障)
}if (inFile.eof()) {// 到达文件末尾
}if (inFile.good()) {// 一切正常
}// 重置错误状态
inFile.clear();

四、文本文件操作

1. 写入文本文件

std::ofstream textOut("data.txt");
if (textOut) {textOut << "Line 1: Hello, World!\n";textOut << "Line 2: The answer is " << 42 << "\n";textOut << "Line 3: Pi ≈ " << 3.14159 << "\n";
}

2. 读取文本文件

std::ifstream textIn("data.txt");
if (textIn) {// 逐行读取std::string line;while (std::getline(textIn, line)) {std::cout << line << std::endl;}// 重置文件指针到开头textIn.clear();textIn.seekg(0);// 按单词读取std::string word;while (textIn >> word) {std::cout << word << " ";}
}

五、二进制文件操作

1. 写入二进制数据

struct Record {int id;char name[50];double balance;
};Record records[3] = {{1, "Alice", 100.50},{2, "Bob", 250.75},{3, "Charlie", 500.25}
};std::ofstream binOut("data.bin", std::ios::binary);
if (binOut) {binOut.write(reinterpret_cast<char*>(records), sizeof(records));
}

2. 读取二进制数据

std::ifstream binIn("data.bin", std::ios::binary);
if (binIn) {// 获取文件大小binIn.seekg(0, std::ios::end);size_t fileSize = binIn.tellg();binIn.seekg(0, std::ios::beg);// 计算记录数量size_t numRecords = fileSize / sizeof(Record);Record* readRecords = new Record[numRecords];// 读取数据binIn.read(reinterpret_cast<char*>(readRecords), fileSize);// 处理数据...delete[] readRecords;
}

六、文件定位

std::fstream file("data.txt", std::ios::in | std::ios::out);if (file) {// 获取当前位置std::streampos pos = file.tellg();// 移动到文件开头file.seekg(0, std::ios::beg);// 移动到文件末尾file.seekg(0, std::ios::end);// 向前移动10字节file.seekg(10, std::ios::cur);// 向后移动5字节file.seekg(-5, std::ios::cur);// 移动到第100字节处file.seekg(100);
}

七、C++17 文件系统库

C++17 引入了 <filesystem> 头文件,提供了更高级的文件操作功能:

#include <filesystem>
namespace fs = std::filesystem;// 创建目录
fs::create_directory("data");// 复制文件
fs::copy_file("source.txt", "data/destination.txt");// 检查文件属性
if (fs::exists("data.txt")) {std::cout << "File size: " << fs::file_size("data.txt") << " bytes\n";std::cout << "Last modified: " << fs::last_write_time("data.txt") << "\n";
}// 遍历目录
for (const auto& entry : fs::directory_iterator(".")) {if (entry.is_regular_file()) {std::cout << "File: " << entry.path() << "\n";} else if (entry.is_directory()) {std::cout << "Directory: " << entry.path() << "\n";}
}// 删除文件
fs::remove("old_data.txt");// 递归删除目录
fs::remove_all("obsolete_data");

八、高级文件操作技巧

1. 内存映射文件(平台特定)

// Windows 示例
#include <windows.h>HANDLE hFile = CreateFile("large.bin", GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
HANDLE hMap = CreateFileMapping(hFile, NULL, PAGE_READONLY, 0, 0, NULL);
char* data = (char*)MapViewOfFile(hMap, FILE_MAP_READ, 0, 0, 0);// 使用 data 指针访问文件内容...UnmapViewOfFile(data);
CloseHandle(hMap);
CloseHandle(hFile);

2. 临时文件处理

#include <cstdio>// 创建临时文件
FILE* tmpFile = tmpfile();
if (tmpFile) {fputs("Temporary data", tmpFile);rewind(tmpFile);char buffer[256];fgets(buffer, sizeof(buffer), tmpFile);std::cout << "Temp content: " << buffer << std::endl;fclose(tmpFile); // 自动删除
}// 使用C++17文件系统
auto tempPath = fs::temp_directory_path() / "tempfile.tmp";
std::ofstream tempOut(tempPath);
// 使用临时文件...
fs::remove(tempPath); // 手动删除

九、错误处理与最佳实践

  1. 始终检查文件操作结果
if (!file) {// 处理错误}
  1. 使用RAII管理资源
{std::ofstream file("data.txt");// 使用文件...
} // 文件自动关闭
  1. 处理大文件
    #ifdef _WIN32// Windows 上处理大于2GB的文件std::ifstream bigFile("large.bin", std::ios::binary | std::ios::ate);bigFile.seekg(0, std::ios::beg);#endif
  1. 跨平台路径处理
// 使用C++17文件系统fs::path filePath = "data";filePath /= "subdir";filePath /= "file.txt";// 输出平台无关路径std::cout << "Path: " << filePath.generic_string() << std::endl;
  1. 异常处理
	std::ifstream file;file.exceptions(std::ifstream::failbit | std::ifstream::badbit);try {file.open("important.txt");// 文件操作...} catch (const std::ios_base::failure& e) {std::cerr << "File error: " << e.what() << std::endl;}

十、性能优化建议

  1. 使用缓冲区
char buffer[4096];std::ifstream inFile("large.bin", std::ios::binary);while (inFile.read(buffer, sizeof(buffer))) {// 处理缓冲区数据}
  1. 减少文件打开/关闭次数
    • 批量处理文件操作
    • 复用文件流对象
  2. 使用内存映射处理大文件
    • 避免多次读写操作
    • 提供随机访问能力
  3. 异步文件I/O
#include <future>auto readFuture = std::async(std::launch::async, []{std::ifstream file("data.bin", std::ios::binary);// 读取操作...});// 主线程继续执行其他任务...readFuture.get(); // 等待读取完成
  1. 选择合适的打开模式

    • 二进制模式避免文本转换开销
    • 追加模式减少文件定位开销

总结

C++提供了丰富的文件操作功能:

  • 基础文本和二进制文件读写
  • 文件定位和状态管理
  • C++17强大的文件系统库
  • 高级技术如内存映射和异步I/O
http://www.xdnf.cn/news/16393.html

相关文章:

  • C++ - 模板进阶
  • 浅谈生成式AI语言模型的现状与展望
  • 自然语言处理技术应用领域深度解析:从理论到实践的全面探索
  • 【STM32】CUBEMX下FreeRTOS 任务栈管理与栈溢出检测(CMSIS_V2接口)
  • 【深入探究系列(6)】算法设计:高效算法的实现与优化
  • 机器学习 KNN 算法,鸢尾花案例
  • DP4871音频放大芯片3W功率单通道AB类立体声/音频放大器
  • Python day24
  • 残月头像阁
  • Vue3中的标签 ref 与 defineExpose:模板引用与组件暴露
  • Java零基础入门学习知识点2-JDK安装配置+Maven
  • vue3 组件生命周期,watch和computed
  • 【ResNet50图像分类部署至RK3588】模型训练→转换RKNN→开发板部署
  • Agent领域,近年来的前沿研究方向:多智能体协作、认知启发架构、伦理安全、边缘计算集成
  • 《计算机组成原理与汇编语言程序设计》实验报告一 基本数字逻辑及汉字显示
  • Avalonia 发布完cv到Linux上运行 出现字体丢失/不显示问题
  • 【C++详解】模板进阶 非类型模板参数,函数模板特化,类模板全特化、偏特化,模板分离编译
  • 【第十二篇】 SpringBoot定时任务
  • 详解FreeRTOS开发过程(八)-- 时间标志
  • HyperWorks教程:HyperWorks助力精准打造游艇的设计
  • SIP广播对讲系统:构建高效智能的语音通信网络
  • 一道检验编码能力的字符串的题目
  • Vue2-VueRouter
  • 刷题日记0725
  • Python,仿生计算新前沿:Python实现进化-强化学习混合算法
  • php语法--foreach和in_array的使用
  • HttpServletRequest知识点
  • 线性代数 下
  • Oracle转Mysql建表脚本
  • RocketMQ常见问题梳理