DEV Community

Kinywa
Kinywa

Posted on

SQL Joins and Window Functions

SQL Joins

What is a Join? A JOIN combines rows from two or more tables based on a related column. They are the backbone of relational databases, spreading data across normalized tables and reuniting it at query time.

Types of Joins

INNER JOIN - returns only rows with a match in both tables.

SELECT e.full_name, d.department_name
FROM employees e
INNER JOIN departments d ON e.department_id = d.id;
Enter fullscreen mode Exit fullscreen mode

LEFT JOIN - returns all rows from the left table; unmatched right-side rows return NULL.

SELECT e.full_name, d.department_name
FROM employees e
LEFT JOIN departments d ON e.department_id = d.id;
Enter fullscreen mode Exit fullscreen mode

RIGHT JOIN - opposite of LEFT JOIN; all rows from the right table are returned.

SELECT e.full_name, d.department_name
FROM employees e
RIGHT JOIN departments d ON e.department_id = d.id;
Enter fullscreen mode Exit fullscreen mode

FULL OUTER JOIN - returns all rows from both tables; NULLs fill the gaps where there's no match.

SELECT e.full_name, d.department_name
FROM employees e
FULL OUTER JOIN departments d ON e.department_id = d.id;
Enter fullscreen mode Exit fullscreen mode

CROSS JOIN - produces the Cartesian product; every row from table A paired with every row from table B.

SELECT products.name, colors.color
FROM products
CROSS JOIN colors;
Enter fullscreen mode Exit fullscreen mode

SELF JOIN - joins a table with itself; perfect for hierarchical data like org charts.

SELECT e1.full_name AS employee, e2.name AS manager
FROM employees e1
INNER JOIN employees e2 ON e1.manager_id = e2.id;
Enter fullscreen mode Exit fullscreen mode

Example:

-- Sales report combining orders, customers and products
SELECT
    c.name        AS customer,
    p.product_name,
    o.order_date,
    o.quantity,
    (o.quantity * p.price) AS total_value
FROM orders o
INNER JOIN customers c ON o.customer_id = c.id
INNER JOIN products  p ON o.product_id  = p.id
WHERE o.order_date >= '2024-01-01'
ORDER BY total_value DESC;
Enter fullscreen mode Exit fullscreen mode

Window Functions

What Are Window Functions? A Window Function performs calculations across a set of rows related to the current row - its window - without collapsing the result set like GROUP BY does. Every row keeps its identity, the function just adds a computed value beside it.

Key Window Functions with sample queries

ROW_NUMBER() - unique sequential number per partition

SELECT full_name, department, salary,
    ROW_NUMBER() OVER (PARTITION BY department ORDER BY salary DESC) AS rank_in_dept
FROM employees;
Enter fullscreen mode Exit fullscreen mode

RANK() vs DENSE_RANK() - RANK skips numbers on ties while DENSE_RANK does not

SELECT full_name, salary,
    RANK()       OVER (ORDER BY salary DESC) AS rank,
    DENSE_RANK() OVER (ORDER BY salary DESC) AS dense_rank
FROM employees;
Enter fullscreen mode Exit fullscreen mode

LAG() / LEAD() - look backwards or forwards without a self-join

SELECT month, revenue,
    LAG(revenue, 1)  OVER (ORDER BY month) AS prev_month,
    LEAD(revenue, 1) OVER (ORDER BY month) AS next_month,
    revenue - LAG(revenue, 1) OVER (ORDER BY month) AS mom_change
FROM monthly_sales;
Enter fullscreen mode Exit fullscreen mode

NTILE(n) - bucket rows into n equal groups

SELECT name, salary,
    NTILE(4) OVER (ORDER BY salary DESC) AS salary_quartile
FROM employees;
Enter fullscreen mode Exit fullscreen mode

Summary

Joins at a glance

  • INNER JOIN - Returns matched rows only
  • LEFT JOIN - Returns all left rows + matched right (NULLs for no match)
  • RIGHT JOIN - Returns all right rows + matched left (NULLs for no match)
  • FULL OUTER JOIN - Returns all rows from both tables, NULLs where unmatched
  • CROSS JOIN - Returns every row combination (Cartesian product)
  • SELF JOIN - Returns a table joined to itself

Window Functions at a glance

  • ROW_NUMBER() - Unique sequential ID per row/partition
  • RANK() / DENSE_RANK() - Rankings with/without tie gaps
  • LAG() / LEAD() - Compare current row to prior/next row
  • SUM() / AVG() as window - Running totals, moving averages
  • NTILE(n) - Percentile buckets
  • FIRST_VALUE() / LAST_VALUE() - First or last value in a window

Joins are like smart VLOOKUPs - they stitch data from multiple tables together using a shared key.

Window Functions are like adding a calculated column to a spreadsheet that is "aware" of its neighbors.

Top comments (0)