Skip to content

Introduction to SQL for Data Analytics

Why SQL is essential

Most analytics work happens where the data lives:

  • Relational databases (PostgreSQL, MySQL, SQLite)
  • Data warehouses (BigQuery, Snowflake, Redshift)

SQL is used to:

  • Retrieve data efficiently
  • Aggregate metrics (DAU, revenue, churn)
  • Join multiple tables (users + orders + events)

Core mental model

  • Data is stored in tables.
  • A query reads rows/columns and returns a result set.
Minimal query
SELECT *
FROM users
LIMIT 10;
Minimal query
SELECT *
FROM users
LIMIT 10;

Typical analytics tables

  • users(user_id, created_at, country, plan)users(user_id, created_at, country, plan)
  • orders(order_id, user_id, order_ts, amount)orders(order_id, user_id, order_ts, amount)
  • events(user_id, event_ts, event_name, device)events(user_id, event_ts, event_name, device)

What you’ll learn in this phase

  • SELECTSELECT, WHEREWHERE, ORDER BYORDER BY, LIMITLIMIT
  • Aggregations: COUNTCOUNT, SUMSUM, AVGAVG
  • GROUP BYGROUP BY, HAVINGHAVING
  • Joins
  • Window functions
  • CTEs
  • Using SQL from Python (pandas)

Where SQL fits in an analytics workflow

You rarely run one query in isolation. The usual shape of the work is: raw tables live in a database, a query filters and reshapes them, and the result lands somewhere you can chart, model, or share.

diagram Where SQL fits in analytics mermaid
Raw tables live in a database; a query filters and shapes them into a result you can chart or model.

The database never changes because you queried it — a SELECTSELECT just reads and returns rows. That’s what makes SQL safe to explore with: you can run the same query a hundred times while you’re figuring out the right filter, and nothing gets damaged.

SQLite: a database in a single file

You don’t need a server to practice SQL. SQLite (Python’s built-in sqlite3sqlite3 module) stores an entire database in one file — or even in memory — which makes it perfect for learning and for the exercises on this page.

A tiny in-memory database
import sqlite3
 
conn = sqlite3.connect(":memory:")
conn.execute("CREATE TABLE users (user_id INTEGER, country TEXT, plan TEXT)")
conn.executemany(
    "INSERT INTO users VALUES (?, ?, ?)",
    [(1, "IN", "free"), (2, "IN", "pro"), (3, "US", "pro")],
)
conn.commit()
 
rows = conn.execute("SELECT * FROM users").fetchall()
print(rows)
A tiny in-memory database
import sqlite3
 
conn = sqlite3.connect(":memory:")
conn.execute("CREATE TABLE users (user_id INTEGER, country TEXT, plan TEXT)")
conn.executemany(
    "INSERT INTO users VALUES (?, ?, ?)",
    [(1, "IN", "free"), (2, "IN", "pro"), (3, "US", "pro")],
)
conn.commit()
 
rows = conn.execute("SELECT * FROM users").fetchall()
print(rows)
text
[(1, 'IN', 'free'), (2, 'IN', 'pro'), (3, 'US', 'pro')]
text
[(1, 'IN', 'free'), (2, 'IN', 'pro'), (3, 'US', 'pro')]

🧪 Try It Yourself

Exercise 1 – Create a table and read it back

Exercise 2 – Filter rows with WHERE

Exercise 3 – Load a query result into pandas

Next

Head to SQL Basics (SELECT, WHERE, ORDER BY, LIMIT) to practice the four clauses you’ll use in almost every query you ever write.

If this helped you, consider buying me a coffee ☕

Buy me a coffee

Was this page helpful?

Let us know how we did