Day 9: File Handling — Reading & Writing Files

🐍 Day 9: File Handling — Reading & Writing Files


1. Learning Objectives

By the end of Day 9, you will be able to:

  • Open, read, and write files using Python's built-in open() function

  • Understand file modes (r, w, a, r+, x) and when to use each

  • Use the with statement as a context manager for safe file handling

  • Read files line by line, as a whole, or into a list

  • Write and append data to files

  • Handle common file-related errors gracefully

  • Process real-world data from text and CSV files


2. Concept Explanation

2.1 Why File Handling? — Persistence Beyond Runtime

So far, all your programs have been volatile — data disappears the moment the program ends. File handling gives your programs persistence:

Without Files With Files
Data lost on exit Data survives between runs
Can't share information Read/write configs, logs, exports
Limited to keyboard input Process gigabytes of existing data

Real-world examples: saving game progress, reading configuration files, processing CSV data, logging events, storing user-generated content.


2.2 The open() Function — Your Gateway to Files

file = open("filename.txt", "mode")

File modes at a glance:

Mode Name What It Does Creates File? Overwrites?
"r" Read Opens for reading (default). Error if file doesn't exist.
"w" Write Opens for writing. Creates file if needed. ✅ (clears existing content)
"a" Append Opens for appending. Creates file if needed. ❌ (writes at end)
"x" Exclusive create Creates a new file. Error if file already exists. ❌ (safe create)
"r+" Read + Write Opens for both reading and writing. ❌ (manual control)
"w+" Write + Read Opens for writing and reading. Overwrites existing.
"a+" Append + Read Opens for appending and reading.

Add "b" for binary mode (e.g., "rb", "wb") when working with images, PDFs, etc.:

# Text mode (default) — for .txt, .csv, .json, etc.
open("data.txt", "r")

# Binary mode — for images, audio, video, etc.
open("photo.jpg", "rb")

2.3 The with Statement — Automatic Cleanup (Best Practice)

Always use with. It automatically closes the file — even if an error occurs.

# ❌ Manual — you might forget to close
file = open("data.txt", "r")
content = file.read()
file.close()  # Easy to forget!

# ✅ with statement — auto-closes
with open("data.txt", "r") as file:
   content = file.read()
# File is automatically closed here — even if an exception occurred

💡 with is a context manager. We'll explore them deeply on Day 18. For now, know that with open(...) as f: is the standard, safe pattern for all file operations.


2.4 Reading Files — Three Ways

Given a file students.txt:

Alice
Bob
Charlie
David

Method 1: .read() — entire file as one string

with open("students.txt", "r") as file:
   content = file.read()
   print(content)
# Output:
# Alice
# Bob
# Charlie
# David

⚠️ Don't use .read() on huge files — it loads everything into memory at once.

Method 2: .readline() — one line at a time

with open("students.txt", "r") as file:
   first_line = file.readline()
   print(first_line)  # "Alice\n"

   second_line = file.readline()
   print(second_line)  # "Bob\n"

Method 3: .readlines() — list of all lines

with open("students.txt", "r") as file:
   lines = file.readlines()
   print(lines)  # ['Alice\n', 'Bob\n', 'Charlie\n', 'David\n']

Method 4: Iterate directly (most Pythonic)

with open("students.txt", "r") as file:
   for line in file:
       print(line.strip())  # .strip() removes the \n
# Output:
# Alice
# Bob
# Charlie
# David

💡 This last method is the best for large files — it reads one line at a time without loading the whole file into memory.


2.5 Writing to Files

.write() — write a single string:

with open("output.txt", "w") as file:
file.write("Hello, World!\n")
file.write("This is line 2.\n")

⚠️ "w" mode erases existing content. If output.txt already had data, it's gone.

.writelines() — write multiple strings from a list:

lines = ["First line\n", "Second line\n", "Third line\n"]
with open("output.txt", "w") as file:
file.writelines(lines)

⚠️ .writelines() does NOT add newlines automatically. You must include \n in each string.


2.6 Appending to Files

"a" mode writes at the end of the file without erasing existing content:

# First run
with open("log.txt", "a") as file:
file.write("First entry\n")

# Second run — adds to the end
with open("log.txt", "a") as file:
file.write("Second entry\n")

# log.txt now contains:
# First entry
# Second entry

This is perfect for logs, journals, or accumulating data over time.


2.7 Working with File Paths

Python's pathlib module (Python 3.4+) is the modern way to handle paths:

from pathlib import Path

# Current working directory
print(Path.cwd())

# Build paths (works on any OS: Windows, Mac, Linux)
data_folder = Path("data")
file_path = data_folder / "students.txt"
print(file_path) # data/students.txt (or data\students.txt on Windows)

# Check if file exists
if file_path.exists():
print("File found!")
else:
print("File not found.")

# Create directory if it doesn't exist
data_folder.mkdir(exist_ok=True)

Traditional os.path (older approach, still common):

import os

if os.path.exists("data/students.txt"):
print("File found!")

2.8 Common Errors & How to Handle Them

Error Cause Solution
FileNotFoundError File doesn't exist in "r" mode Check path, or use try/except (Day 10)
PermissionError No permission to read/write Check file permissions
IsADirectoryError Tried to open a directory as a file Check if path points to a directory
UnicodeDecodeError Wrong encoding (e.g., reading binary as text) Specify encoding: open(..., encoding="utf-8")
Forgot to close file Manual open() without .close() Use with — always

Specifying encoding (important for non-English text):

with open("data.txt", "r", encoding="utf-8") as file:
content = file.read()

2.9 Quick Reference: Reading Patterns

# Read entire file
with open("file.txt", "r") as f:
text = f.read()

# Read line by line (best for large files)
with open("file.txt", "r") as f:
for line in f:
print(line.strip())

# Read into a list
with open("file.txt", "r") as f:
lines = f.readlines()

# Write (overwrites)
with open("file.txt", "w") as f:
f.write("Hello\n")

# Append (adds to end)
with open("file.txt", "a") as f:
f.write("More content\n")

3. Code Examples

Example 1: Simple Note-Taking App

from datetime import datetime

def add_note():
"""Append a timestamped note to a file."""
note = input("Write your note: ")
timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
with open("notes.txt", "a") as file:
file.write(f"[{timestamp}] {note}\n")
print("Note saved!")

def read_all_notes():
"""Read and display all notes."""
try:
with open("notes.txt", "r") as file:
content = file.read()
if content:
print("\n=== YOUR NOTES ===")
print(content)
else:
print("No notes yet.")
except FileNotFoundError:
print("No notes yet. Add one first!")

# Menu
while True:
choice = input("\n[A]dd note [V]iew notes [Q]uit: ").lower()
if choice == "a":
add_note()
elif choice == "v":
read_all_notes()
elif choice == "q":
break

Example 2: Copy a File

def copy_file(source, destination):
"""Copy contents from source file to destination file."""
with open(source, "r") as src:
content = src.read()
with open(destination, "w") as dst:
dst.write(content)
print(f"Copied '{source}' → '{destination}'")

copy_file("original.txt", "backup.txt")

Example 3: CSV Reader (Preview of Real-World Data)

# Sample grades.csv:
# Name,Score
# Alice,85
# Bob,92
# Charlie,78

def read_grades(filename):
"""Read a CSV file and return a list of (name, score) tuples."""
results = []
with open(filename, "r") as file:
next(file) # Skip header line
for line in file:
name, score = line.strip().split(",")
results.append((name, int(score)))
return results

grades = read_grades("grades.csv")
for name, score in grades:
print(f"{name}: {score}")

4. Hands-On Exercises

Exercise 1: File Writer

Ask the user for their name, age, and city. Write this information to a file called profile.txt, one piece of data per line.

Exercise 2: File Reader & Counter

Write a program that reads a text file and prints:

  • Total number of lines

  • Total number of words

  • Total number of characters

Exercise 3: Log File Generator

Write a program that keeps asking the user for log messages. Append each message with a timestamp to application.log. Stop when the user types "exit".

Exercise 4: Search in File

Write a program that asks for a search word and a filename. Print every line from that file that contains the search word (case-insensitive). Handle FileNotFoundError gracefully.

Exercise 5: Reverse File

Read all lines from input.txt, reverse their order, and write them to output.txt. (First line becomes last, last becomes first.)


5. Applied Challenge Task 🏗️

Personal Journal Application

Build a journal program that:

  1. Creates a new journal entry: Prompts for a title and body text. Saves the entry as a .txt file in a journal/ folder. The filename should be the date (e.g., 2026-05-07.txt).

  2. Views an entry: Lists all available journal files and lets the user pick one to read.

  3. Lists all entries: Shows a table of all entries with their dates and titles.

  4. Searches entries: Lets the user type a keyword and shows which entries contain it.

Entry file format:

Title: My Great Day
---
Today I learned about file handling in Python. It's amazing how
easy it is to read and write files with the with statement!

Example run:

=== MY JOURNAL ===
[N]ew entry [V]iew entry [L]ist all [S]earch [Q]uit
> N
Title: A Productive Day
Write your entry (type END on a new line to finish):
Today I finished Day 9 of Python.
I can now read and write files.
END
Entry saved!

> L
=== JOURNAL ENTRIES ===
2026-05-06: My Great Day
2026-05-07: A Productive Day

Stretch goals:

  • Add edit functionality (overwrite an existing entry)

  • Add delete functionality (remove an entry file)

  • Use pathlib.Path for all file operations

  • Export all entries to a single combined file


6. Brief Review Summary

Concept Key Points
open() Opens a file — requires mode ("r", "w", "a", etc.)
with Context manager — automatically closes the file (best practice)
.read() Reads entire file as a string
.readlines() Reads entire file into a list of lines
.write() Writes a string to file
.writelines() Writes a list of strings (add \n yourself)
"w" mode Overwrites existing file; creates if not found
"a" mode Appends to end; creates if not found
"r" mode Read-only; error if file doesn't exist
pathlib Modern, cross-platform path handling
Encoding Specify encoding="utf-8" for non-ASCII text

7. Preview of Next Topic — Day 10

Tomorrow we'll learn to make your programs robust and crash-proof:

  • Exception Handlingtry, except, finally, else

  • Catching specific vs. generic exceptions

  • Raising your own exceptions with raise

  • Debugging techniques and reading tracebacks

  • Writing code that fails gracefully


🎯 Your Action Items for Day 9:

  1. ✅ Complete all 5 exercises

  2. ✅ Build the Personal Journal Application

  3. ✅ Experiment with different file modes — break things intentionally

  4. ✅ Try pathlib.Path for navigating your file system


Need this saved? Say "Save to Google Docs". Need help? Just ask. Ready for Day 10? Say "Start Day 10"! 🚀


Comments

Popular posts from this blog

Day 1: Welcome to Python — Your Journey Begins

Python: Your Gateway to Coding Adventures

Day 11: List Comprehensions & Lambda Functions

Earn From the Comfort of Your Home

Build the skills to work comfortably from home, on your own terms.

Get Started Today