Trabajo con el sistema de archivos en C++: desde lo básico hasta técnicas avanzadas
Trabajar con el sistema de archivos es una de las tareas fundamentales en el desarrollo en C++. Ya sea guardar configuraciones de aplicaciones, procesar logs o crear sistemas complejos de gestión de datos — saber leer, escribir y manipular archivos y directorios es necesario para todo desarrollador de C++. En este artículo veremos tanto los métodos clásicos de trabajo con archivos mediante fstream, como el enfoque moderno usando la biblioteca std::filesystem (C++17 y posteriores).
Fundamentos del trabajo con archivos: biblioteca fstream
La biblioteca fstream (<fstream>) proporciona tres clases principales para trabajar con archivos:
ifstream— para lectura de archivos (input file stream);ofstream— para escritura en archivos (output file stream);fstream— para lectura y escritura simultáneas.
Lectura de datos desde un archivo
Veamos un ejemplo muy simple de apertura y lectura de un archivo de texto línea por línea:
#include <iostream>#include <fstream>#include <string>
int main() { std::ifstream inputFile("data.txt"); if (!inputFile.is_open()) { std::cerr << "¡Error al abrir el archivo!" << std::endl; return 1; }
std::string line; while (std::getline(inputFile, line)) { std::cout << line << std::endl; }
inputFile.close(); return 0;}Es importante verificar siempre el éxito de la apertura del archivo usando el método is_open(). El archivo se cerrará automáticamente al salir del ámbito, pero la llamada explícita a close() se considera una buena práctica.
Escritura de datos en un archivo
La escritura en un archivo se realiza de manera similar a la salida en consola — con el operador <<:
#include <fstream>
int main() { std::ofstream outputFile("output.txt"); if (!outputFile) { std::cerr << "¡No se pudo crear el archivo!" << std::endl; return 1; }
outputFile << "Línea 1" << std::endl; outputFile << "Línea 2" << std::endl; outputFile << 42 << std::endl; // los números se escriben automáticamente como texto
outputFile.close(); return 0;}Por defecto, ofstream sobrescribe el archivo. Para añadir datos al final, use la bandera std::ios::app:
std::ofstream outputFile("log.txt", std::ios::app);Archivos binarios y acceso aleatorio
Para trabajar con datos binarios, use la bandera std::ios::binary. Los métodos read() y write() permiten trabajar con bloques de memoria:
#include <fstream>
struct Record { int id; char name[50];};
int main() { // Escritura de estructura Record rec = {1, "Ejemplo"}; std::ofstream binOut("data.bin", std::ios::binary); binOut.write(reinterpret_cast<char*>(&rec), sizeof(rec)); binOut.close();
// Lectura de estructura Record recIn; std::ifstream binIn("data.bin", std::ios::binary); binIn.read(reinterpret_cast<char*>(&recIn), sizeof(recIn)); binIn.close();
return 0;}Para posicionarse dentro del archivo, use seekg() (para entrada) y seekp() (para salida) con los parámetros std::ios::beg, std::ios::cur o std::ios::end.
C++ moderno: biblioteca std::filesystem
A partir de C++17, la biblioteca estándar incluye el módulo std::filesystem, que simplifica significativamente el trabajo con el sistema de archivos. Proporciona funciones convenientes para la manipulación de rutas, archivos y directorios.