C++ fstream

File input and output operations in C++

📁 What is fstream?

The fstream library enables file operations in C++. It provides classes to read from and write to files, allowing programs to store and retrieve data permanently on disk storage.


#include <fstream>
#include <iostream>
using namespace std;

int main() {
    ofstream file("example.txt");
    file << "Hello, File!" << endl;
    file.close();
    return 0;
}
                                    

fstream Classes

📝

ofstream

Output file stream for writing to files

ofstream outFile("data.txt");
outFile << "Writing to file";
📖

ifstream

Input file stream for reading from files

ifstream inFile("data.txt");
string line;
getline(inFile, line);
🔄

fstream

File stream for both reading and writing

fstream file("data.txt", ios::in | ios::out);
⚙️

File Modes

Different modes for file operations

ios::in, ios::out, ios::app, ios::binary

🔹 Writing to Files

Writing data to files in C++ is efficiently handled using the ofstream (output file stream) class from the <fstream> library. This process involves creating a stream object, opening a file in write mode, and using the insertion operator (<<) to output data, just like writing to the console with cout. It's essential to check if the file opened successfully and to close it after operations to ensure data integrity and free system resources. This mechanism is fundamental for creating configuration files, saving user data, logging program output, and generating reports.

#include <fstream>
#include <iostream>
using namespace std;

int main() {
    // Create and open a file for writing
    ofstream outFile("student.txt");
    
    // Check if file opened successfully
    if (outFile.is_open()) {
        // Write data to file
        outFile << "Student Information" << endl;
        outFile << "Name: John Smith" << endl;
        outFile << "Age: 20" << endl;
        outFile << "Grade: A" << endl;
        
        // Close the file
        outFile.close();
        cout << "Data written to file successfully!" << endl;
    } else {
        cout << "Unable to open file for writing!" << endl;
    }
    
    return 0;
}

Output:

Data written to file successfully!

File "student.txt" created with the student information.

🔹 Reading from Files

Reading data from files is accomplished using the ifstream (input file stream) class, allowing programs to access and process persistent external data. Similar to reading from cin, you can use the extraction operator (>>) for formatted input or functions like getline() to read entire lines, including spaces. Proper error handling, such as checking the file's state after opening, is crucial to prevent runtime errors if a file is missing or corrupted. This capability is vital for loading saved game states, reading configuration parameters, processing datasets, and parsing text-based files.

#include <fstream>
#include <iostream>
#include <string>
using namespace std;

int main() {
    // Open file for reading
    ifstream inFile("student.txt");
    string line;
    
    // Check if file opened successfully
    if (inFile.is_open()) {
        cout << "Reading from file:" << endl;
        cout << "==================" << endl;
        
        // Read file line by line
        while (getline(inFile, line)) {
            cout << line << endl;
        }
        
        // Close the file
        inFile.close();
    } else {
        cout << "Unable to open file for reading!" << endl;
    }
    
    return 0;
}

Output:

Reading from file:
==================
Student Information
Name: John Smith
Age: 20
Grade: A

🔹 Appending to Files

Appending data to existing files prevents overwriting and preserves previous content, a common requirement for logs and data collection. This is done by opening the file stream with the ios::app (append) mode flag, which positions the write pointer at the end of the file. Using ofstream with this flag ensures that every write operation adds to the file's tail. It's a best practice for applications like activity logging, continuously recording sensor data, adding new user entries to a database file, or maintaining audit trails where historical information must be retained and sequentially updated.

#include <fstream>
#include <iostream>
using namespace std;

int main() {
    // Open file in append mode
    ofstream outFile("student.txt", ios::app);
    
    if (outFile.is_open()) {
        // Append new data
        outFile << "Course: Computer Science" << endl;
        outFile << "Semester: Fall 2024" << endl;
        
        outFile.close();
        cout << "Data appended to file successfully!" << endl;
    } else {
        cout << "Unable to open file for appending!" << endl;
    }
    
    return 0;
}

Output:

Data appended to file successfully!

New lines added to existing "student.txt" file.

🔹 File Operations Example

Robust file handling combines reading, writing, and appending with comprehensive error checking to build resilient software. A complete example includes verifying file existence, handling exceptions during open/write/read operations, and ensuring streams are properly closed. Using conditional checks on stream states (like fail() or !is_open()) allows the program to respond gracefully to issues. This level of diligence is critical for enterprise applications, financial software, and any system where data loss or corruption due to file errors would have significant consequences.

#include <fstream>
#include <iostream>
#include <string>
using namespace std;

int main() {
    string filename = "numbers.txt";
    
    // Write numbers to file
    ofstream outFile(filename);
    if (outFile.is_open()) {
        for (int i = 1; i <= 5; i++) {
            outFile << "Number " << i << ": " << i * 10 << endl;
        }
        outFile.close();
        cout << "Numbers written to file." << endl;
    }
    
    // Read numbers from file
    ifstream inFile(filename);
    if (inFile.is_open()) {
        string line;
        cout << "\nReading from file:" << endl;
        while (getline(inFile, line)) {
            cout << line << endl;
        }
        inFile.close();
    }
    
    // Check if file exists
    ifstream checkFile(filename);
    if (checkFile.good()) {
        cout << "\nFile exists and is accessible." << endl;
        checkFile.close();
    } else {
        cout << "\nFile does not exist or cannot be accessed." << endl;
    }
    
    return 0;
}

Output:

Numbers written to file.

Reading from file:
Number 1: 10
Number 2: 20
Number 3: 30
Number 4: 40
Number 5: 50

File exists and is accessible.

🧠 Test Your Knowledge

Which class is used to write data to a file?