Skip to main content

Welcome to a Grasp lesson

Create a free account to keep studying and create your own study path.

Lesson 48

Reading and Writing Files

Recommended resources

Hello! Welcome back to our journey into Python for business analysis.

In our last lesson, you mastered the art of string manipulation—cleaning, extracting, and formatting text data. This is a crucial skill, as you saw when we turned messy log data into a polished report using f-strings. But a script that only works with data typed directly into it has limited use. The real power comes when your code can interact with the outside world.

Today, we'll bridge that gap by learning how to read from and write to simple text and CSV files. This is the foundation of almost every data task you'll perform. As a Business Analyst, you'll constantly be given data exports from databases, ad servers, or CRMs, often in CSV format. You'll need to write scripts to read this data, analyze it (using the string skills you just learned!), and write your findings into new files for reporting or further processing.

We will cover two main topics:

  1. Handling Plain Text Files (.txt): How to read raw text and write your own notes or simple logs.
  2. Working with CSV Files (.csv): The right way to read and write structured, tabular data, which is the bread and butter of data exchange.

By the end of this lesson, you'll be able to build your first simple, end-to-end data processing workflow.

1. Reading and Writing Simple Text Files

Let's start with the basics: plain text files (.txt). While less common for structured data, they are often used for logs, notes, or configuration files. The fundamental process involves three steps: opening the file, performing an action (read or write), and closing it.

To ensure files are always closed properly, even if errors occur, Python provides a clean and safe syntax called a context manager, which uses the with keyword. This is the standard you should always use.

with open('filename.txt', 'mode') as file_variable:
    # Perform operations on the file here
# The file is automatically closed when this block is exited

The 'mode' tells Python what you want to do:

  • 'r': Read (default). Throws an error if the file doesn't exist.
  • 'w': Write. Overwrites the entire file if it exists, or creates a new one if it doesn't.
  • 'a': Append. Adds new content to the end of an existing file, or creates a new one if it doesn't.

Importing and Writing Text Files in Python

The article 'Importing and Writing Text Files in Python' from DataCamp provides concise, practical examples of these operations. We'll use it as our guide for this section.

First, read the section 'Importing text files with Python’s built-in open() function' to see how to read a file line by line inside a with block. Next, read 'Writing text files using the built-in write() method' to understand how to use the 'w' (write) and 'a' (append) modes.

A Practical Example

Let's combine what we've learned. Imagine you have a file, raw_notes.txt, with some messy, user-entered notes:

raw_notes.txt:

  first idea: need to check campaign performance
  Second Idea: update stakeholder list
third idea: ANALYZE Q3 CLICK DATA  

Our goal is to read this file, clean up each line (trim whitespace, standardize to sentence case), and write the cleaned notes to a new file, cleaned_notes.txt.

# Open the input file for reading and create a new file for writing
with open('raw_notes.txt', 'r') as infile, open('cleaned_notes.txt', 'w') as outfile:
    # Loop through each line in the input file
    for line in infile:
        # Use string methods from our last lesson!
        cleaned_line = line.strip().capitalize()
        
        # Write the cleaned line to the output file, adding a newline character
        outfile.write(cleaned_line + '\n')

print("File has been cleaned and saved as cleaned_notes.txt")

After running this, cleaned_notes.txt will contain:

First idea: need to check campaign performance
Second idea: update stakeholder list
Third idea: analyze q3 click data

This simple script demonstrates a complete workflow: reading raw data, transforming it, and loading it into a new file.


2. The Power of CSV for Structured Data

Most business data isn't just a list of notes; it's tabular, with rows and columns. The Comma-Separated Values (CSV) format is the universal standard for exchanging this kind of data.

You might be tempted to read a CSV file and just use line.split(','), but this is unreliable. What if a text field contains a comma, like "New York, NY"? Your simple split would break. Python's built-in csv module is designed to handle these complexities gracefully.

To get a solid grasp of how to use this module, we'll watch a comprehensive video tutorial.

Python Tutorial: CSV Module - How to Read, Parse, and Write CSV Files

The video 'Python Tutorial: CSV Module' by Corey Schafer is one of the best resources for this topic. It clearly explains how to read, parse, and write CSV files using the standard Python library.

Please watch the video from the beginning until 15:04. It's broken down into logical parts: Reading with csv.reader (0:00 - 4:53): See how to read a CSV file where each row becomes a list of strings. Writing with csv.writer (4:53 - 9:11): Learn to write data to a new CSV, and see how the module handles special cases like custom delimiters. Reading files with different delimiters (9:11 - 10:39): This reinforces the concept of delimiters. Reading with csv.DictReader (10:39 - 12:26): This is a key part. Notice how much more readable the code becomes when you can access data by column name (e.g., row['email']) instead of by index (row[2]). Writing with csv.DictWriter (12:26 - 15:04): The counterpart to DictReader. This is the preferred method for writing structured data as it's explicit and less prone to errors.

Why DictReader and DictWriter are a BA's Best Friends

As you saw in the video, csv.reader returns a list, like ['John', 'Doe', 'john.doe@example.com']. To get the email, you need to remember it's at index 2.

csv.DictReader, however, returns a dictionary-like object: {'first_name': 'John', 'last_name': 'Doe', 'email': 'john.doe@example.com'}. Now you can access the email with row['email']. This makes your code:

  • More Readable: It's immediately clear what data you're working with.
  • More Robust: If someone adds a new column to the CSV file, your code won't break as long as the column names you use still exist. With csv.reader, adding a column would shift all the indices and break your code.

For these reasons, you should almost always prefer DictReader and DictWriter when working with tabular data.

Test your understanding!

You are given a row of data from a DictReader object:
row = {'CampaignID': 'CAMP123', 'Spend': '500.25', 'Clicks': '1500'}

Write a single line of Python code to extract the number of clicks and convert it to an integer.

Show answer
clicks_as_integer = int(row['Clicks'])
print(clicks_as_integer) # Output: 1500

This shows the power of accessing data by a descriptive key ('Clicks') rather than a magic number index.


3. Putting It All Together: An AdTech Analysis Task

Let's apply everything to a practical mini-project relevant to your AdTech background.

You've been given a file, ad_performance.csv, containing raw data from a campaign.

ad_performance.csv:

campaign_name,impressions,clicks,spend
Summer_Sale_2024, 50000, 2500, "$1,250.50"
Winter_Promo, 120000, 3600, "$2,800.00"
Back_to_School, 85000, 4000, "$1,950.75"

Notice the data has issues: spaces around the numbers and a dollar sign and comma in the spend column.

Your task:

  1. Read ad_performance.csv.
  2. For each campaign, calculate the Click-Through Rate (CTR), where CTR = (Clicks / Impressions) * 100.
  3. Calculate the Cost Per Click (CPC), where CPC = Spend / Clicks.
  4. Write a new file, campaign_report.csv, with the original data plus the two new metrics (CTR and CPC), ensuring all numbers are formatted cleanly.

Here is the complete script to accomplish this. Read through it carefully, paying attention to the comments.

import csv

# Define the headers for our output file. This includes our new calculated fields.
fieldnames = ['campaign_name', 'impressions', 'clicks', 'spend', 'ctr', 'cpc']

# Use 'with' to open both input and output files
with open('ad_performance.csv', mode='r', encoding='utf-8') as infile, \
     open('campaign_report.csv', mode='w', newline='', encoding='utf-8') as outfile:
    
    # Use DictReader for robust reading
    reader = csv.DictReader(infile)
    
    # Use DictWriter and pass it the fieldnames for the output file
    writer = csv.DictWriter(outfile, fieldnames=fieldnames)
    
    # Write the header row to our new file
    writer.writeheader()
    
    print("Processing campaign data...")
    
    # Loop through each row in the input file (each row is a dictionary)
    for row in reader:
        # --- Transformation Step ---
        # Clean and convert data types, using skills from the previous lesson
        impressions = int(row['impressions'].strip())
        clicks = int(row['clicks'].strip())
        
        # Clean the 'spend' string and convert to a float
        spend_str = row['spend'].strip().replace('$', '').replace(',', '')
        spend = float(spend_str)
        
        # Calculate our new metrics
        # Avoid division by zero if impressions or clicks are 0
        ctr = (clicks / impressions) * 100 if impressions > 0 else 0
        cpc = spend / clicks if clicks > 0 else 0
        
        # --- Prepare the output row ---
        # The writerow method expects a dictionary. We can update the original 'row' dictionary
        # with our new, calculated values.
        row['spend'] = f"{spend:,.2f}" # Format spend back to a clean string
        row['ctr'] = f"{ctr:.2f}%"  # Format CTR as a percentage string
        row['cpc'] = f"${cpc:.2f}"   # Format CPC as a currency string
        
        # Write the complete, transformed row to the output file
        writer.writerow(row)

print("Report 'campaign_report.csv' has been successfully generated.")

After running this script, you will have a new file, campaign_report.csv, that looks like this:

campaign_report.csv:

campaign_name,impressions,clicks,spend,ctr,cpc
Summer_Sale_2024,50000,2500,"1,250.50",5.00%,$0.50
Winter_Promo,120000,3600,"2,800.00",3.00%,$0.78
Back_to_School,85000,4000,"1,950.75",4.71%,$0.49

This example is a microcosm of what you'll do as a BA: take raw data, clean it, enrich it with new calculations, and present it in a structured, readable format.


Conclusion

Congratulations! You've just learned one of the most fundamental and practical skills in programming for data analysis. You can now confidently get data out of files and save your results back, forming a complete analytical workflow.

Key Takeaways:

  • Always use with open(...): It's the safest and cleanest way to handle files in Python.
  • Know your modes: Use 'r' for reading, 'w' for overwriting, and 'a' for appending.
  • Use the csv module for CSV files: It handles the format's complexities, so you don't have to.
  • Prefer DictReader and DictWriter: They make your code for handling tabular data more readable, robust, and less prone to errors.

Preview of the Next Lesson:
So far, we've only used Python's built-in capabilities. While powerful, the real magic of Python for data analysis comes from its vast ecosystem of external packages. The csv module is great, but a package like pandas can read that same CSV file in one line and provide much more powerful tools for analysis.

In our next lesson, we will learn how to understand and install external packages using pip, Python's package manager. This will unlock a whole new level of efficiency and capability for your data analysis tasks.