Data Visualization with Python: Charts That Actually Tell a Story

The difference between a junior and senior data analyst isn’t SQL skills or Python knowledge – it’s the ability to make data tell a story through visualization. Most people create charts that are technically correct but communicate nothing. Let’s fix that.

Rule 1: Choose the Right Chart Type

This sounds obvious but it’s where most people go wrong:

  • Comparing categories: Bar chart (horizontal for many categories)
  • Showing trends over time: Line chart
  • Showing distribution: Histogram or box plot
  • Showing relationships: Scatter plot
  • Showing composition: Stacked bar or area chart
  • Showing proportions: NOT a pie chart. Use a bar chart instead

Making Matplotlib Not Look Terrible

import matplotlib.pyplot as plt
import numpy as np

# The default matplotlib style is ugly. Fix it:
plt.style.use('seaborn-v0_8-whitegrid')
plt.rcParams['figure.figsize'] = (10, 6)
plt.rcParams['font.size'] = 12

months = ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun']
revenue = [45000, 52000, 48000, 61000, 55000, 67000]

fig, ax = plt.subplots()
bars = ax.bar(months, revenue, color='#4361ee', width=0.6)

# Add value labels on bars
for bar, val in zip(bars, revenue):
    ax.text(bar.get_x() + bar.get_width()/2, bar.get_height() + 1000,
            f'${val:,.0f}', ha='center', fontsize=10)

ax.set_title('Monthly Revenue - Q1/Q2 2025', fontsize=16, fontweight='bold', pad=20)
ax.set_ylabel('Revenue ($)')
ax.spines['top'].set_visible(False)
ax.spines['right'].set_visible(False)
plt.tight_layout()
plt.savefig('revenue.png', dpi=150, bbox_inches='tight')

Those few extra lines – removing top/right spines, adding value labels, using a better color – transform a chart from “default homework assignment” to “professional report.”

Seaborn for Statistical Charts

import seaborn as sns
import pandas as pd

# Distribution comparison
fig, ax = plt.subplots(figsize=(10, 6))
sns.boxplot(data=df, x='department', y='salary', palette='viridis', ax=ax)
ax.set_title('Salary Distribution by Department', fontsize=16, fontweight='bold')
plt.xticks(rotation=45)
plt.tight_layout()

The One-Chart-One-Message Rule

Every chart should answer exactly one question. If your chart needs a paragraph to explain, it’s too complex. Split it into multiple charts.

Bad: A chart showing revenue, cost, profit, and customer count on the same axes with four different colors.

Good: Four separate charts, each highlighting one metric with a clear title.

Color Tips

  • Use a single color with varying shades for sequential data
  • Use distinct colors only when comparing categories (max 5-6 colors)
  • Highlight the important data point with a bright color, grey out the rest
  • Consider colorblind-friendly palettes (viridis, cividis)

Annotations Make Charts Memorable

# Point to an interesting event
ax.annotate('Product launch', xy=('Mar', 48000), 
            xytext=('Apr', 43000),
            arrowprops=dict(arrowstyle='->', color='red'),
            fontsize=11, color='red', fontweight='bold')

Adding context – marking events, thresholds, or anomalies – transforms a chart from data display into a narrative.

Great visualization isn’t about fancy tools or complex code. It’s about making one clear point, removing everything that doesn’t support that point, and making it easy for anyone to understand at a glance.

Leave a Comment

Your email address will not be published. Required fields are marked *

Scroll to Top