C++ Input / Output & File Handling

Stream Classes & File I/O

Learn how C++ uses streams to transfer data between programs and devices — covering file handling, error checking, operator overloading, and string streams.

TOPIC 01

Stream Classes

cin, cout, ifstream, ofstream — the four pillars of C++ I/O.

TOPIC 02

File I/O

Read and write data to disk files using stream objects.

TOPIC 03

File Pointers

Control read/write positions using seekg() and seekp().

TOPIC 04

Operator Overloading

Customize << and >> for user-defined class objects.

TOPIC 05

String Streams

Use memory like a stream with stringstream.

TOPIC 06

Command-Line Args

Pass values into programs at startup via argc and argv.

🌊

What is a Stream?

In C++, a stream is a flow of data. It is used to transfer data between the program and input/output devices. Instead of directly handling hardware, we use streams as a bridge — making programming simple and portable.

⌨️
Keyboard
Input device
🌊
cin stream
data flows in
💻
Program
processes data
🌊
cout stream
data flows out
🖥️
Screen
Output device
Types of Stream Classes
Class Header Purpose Direction
cin <iostream> Input from keyboard Keyboard → Program
cout <iostream> Output to screen Program → Screen
ifstream <fstream> Input from file File → Program
ofstream <fstream> Output to file Program → File
⚠️

Stream Errors

Streams can have errors during input/output operations. It is important to detect and handle them to prevent crashes or incorrect data.

Common Error Types
  • End of file reached unexpectedly
  • Invalid or unexpected input type
  • File not found or not opened
Error Checking Functions
CHECK

fail()

Returns true if a read or write operation has failed.

CHECK

eof()

Returns true if end of file has been reached.

CHECK

good()

Returns true if the stream is in a valid, error-free state.

stream_error.cpp C++
if(file.fail()) {
    cout << "Error opening file";
}

if(file.eof()) {
    cout << "End of file reached";
}

if(file.good()) {
    cout << "Stream is healthy";
}
💾

Disk File I/O with Streams

C++ uses streams to read and write files stored on disk. The <fstream> header provides two main classes for this purpose.

ofstream — Write
ofstream fout("test.txt");
fout << "Hello File";
fout.close();
ifstream — Read
ifstream fin("test.txt");
string data;
fin >> data;
fin.close();
Complete Program Example
file_io.cpp C++
#include<iostream>
#include<fstream>
using namespace std;

int main() {
    // Writing to file
    ofstream fout("test.txt");
    fout << "Hello File";
    fout.close();

    // Reading from file
    ifstream fin("test.txt");
    string data;
    fin >> data;
    cout << data;
    fin.close();
}
▶ Output
Hello
✅ Always call close() after finishing file operations to flush data and release resources.
🎯

File Pointers

Every file stream has internal pointers that track the current position for reading and writing. These can be moved manually for precise control.

get pointer (gptr)
// Used during reading
file.seekg(0);     // move to start
file.seekg(5);     // skip 5 bytes
put pointer (pptr)
// Used during writing
file.seekp(0);     // move to start
file.seekp(5);     // skip 5 bytes
Program Example
file_pointer.cpp C++
#include<iostream>
#include<fstream>
using namespace std;

int main() {
    fstream file("abc.txt", ios::in | ios::out);

    file << "Hello World";
    file.seekg(0);          // move read pointer to beginning

    char ch;
    file.get(ch);           // read first character
    cout << ch;
}
▶ Output
H
🛡️

Error Handling in File I/O

Before reading or writing, always verify the file opened successfully. A failed file open will cause incorrect behavior or crashes if not handled.

Common File Errors
  • File not found at the given path
  • File not opened due to permission issues
  • File opened in wrong mode (e.g., reading a write-only file)
file_error.cpp C++
#include<iostream>
#include<fstream>
using namespace std;

int main() {
    ifstream file("data.txt");

    if(!file) {                   // check if file opened
        cout << "File not found";
        return 0;
    }

    string data;
    file >> data;
    cout << data;
}
⚠️ Always check if(!file) or file.fail() immediately after opening a file — never assume it succeeded.
🎓

File I/O with Member Functions

We can store and retrieve entire objects in binary files using the write() and read() member functions. This is useful for saving class data persistently.

💡 (char*)&s casts the object to a character pointer so it can be written as raw bytes. sizeof(s) tells how many bytes to write.
object_file.cpp C++
#include<iostream>
#include<fstream>
using namespace std;

class Student {
public:
    int id;
    char name[20];

    void getData() {
        cin >> id >> name;
    }
    void showData() {
        cout << id << " " << name;
    }
};

int main() {
    Student s;

    // Write object to binary file
    ofstream file("student.dat");
    s.getData();
    file.write((char*)&s, sizeof(s));
    file.close();

    // Read object back from file
    ifstream file2("student.dat");
    file2.read((char*)&s, sizeof(s));
    s.showData();
}
⚙️

Operator Overloading (<< and >>)

We can overload the << and >> operators to allow cin and cout to work directly with user-defined class objects — just like built-in types.

<< Output Operator
friend ostream& operator<<(
    ostream& out, Test t) {
    out << t.x;
    return out;
}
>> Input Operator
friend istream& operator>>(
    istream& in, Test &t) {
    in >> t.x;
    return in;
}
Complete Program Example
op_overload.cpp C++
#include<iostream>
using namespace std;

class Test {
public:
    int x;

    friend ostream& operator<<(ostream& out, Test t) {
        out << t.x;
        return out;
    }

    friend istream& operator>>(istream& in, Test &t) {
        in >> t.x;
        return in;
    }
};

int main() {
    Test t;
    cin  >> t;    // uses overloaded >>
    cout << t;    // uses overloaded <<
}
💡 Both operators are declared as friend functions because they need access to the private data of the class, and must take the stream as their first parameter.
🧠

Memory as Stream Object (String Streams)

C++ allows using memory like a stream with stringstream from the <sstream> header. This is useful for converting between types or building strings dynamically.

stringstream.cpp C++
#include<iostream>
#include<sstream>
using namespace std;

int main() {
    stringstream ss;
    ss << 100;       // write integer to string stream

    int x;
    ss >> x;         // read it back as integer

    cout << x;
}
▶ Output
100
stringstream is commonly used for type conversions — e.g., converting integers to strings or parsing comma-separated values.
💬

Command-Line Arguments

Command-line arguments are values passed to the program when it is launched from the terminal. They are received through the main() function's parameters.

argc
// Argument Count
// Total number of arguments
// including the program name
argv[ ]
// Argument Vector
// Array of strings
// argv[0] = program name
cmdargs.cpp C++
#include<iostream>
using namespace std;

int main(int argc, char* argv[]) {
    cout << "Number of arguments: " << argc    << endl;
    cout << "First argument: "      << argv[0] << endl;
}
💡 When you run ./myProgram Hello, argc is 2 and argv[0] is myProgram, argv[1] is Hello.
🖨️

Printer Output

C++ does not directly control printers like modern GUI applications. Instead, the standard approach is to write data to a file and then send that file to the printer.

printer.cpp C++
ofstream file("print.txt");
file << "Print this text";
file.close();
// Then open the file and print manually or via OS command
📄 Write your content to a .txt file, then use the operating system's print dialog or a command like lp print.txt on Linux to send it to a printer.

Frequently Asked Questions

01 What is a stream in C++?
A stream is a flow of data between a program and a device (keyboard, screen, or file). It abstracts hardware interaction into a simple, unified interface.
02 What is file I/O?
File I/O means reading data from files and writing data to files using ifstream and ofstream stream objects from the <fstream> header.
03 What is seekg()?
The seekg() function moves the get (read) pointer to a specific position in the file, allowing random-access reading.
04 What is stringstream?
A stringstream treats a memory string like a stream, enabling easy type conversions and parsing without actual file or device I/O.
05 What are command-line arguments?
Values passed to the program at startup through the terminal. Received via argc (count) and argv[] (array of strings) in main().

🎯 Conclusion

Streams and file handling in C++ are essential for working with input and output beyond the console. They allow programs to read and write files, handle errors, and manage data efficiently. Concepts like file pointers, operator overloading, and string streams make programs more powerful and flexible. Start with simple file read/write, then move to advanced topics like objects and operator overloading.