SELECT basics

The fundamentals of SQL queries — projection, filtering, sorting, and the order they actually run in.

⏱ 6 min read Beginner SQL Updated May 2026

What you'll learn

  • How a SELECT statement is built up
  • The logical execution order (it's NOT what you write)
  • Practical patterns for filtering and sorting

SELECT is the verb you’ll use more than any other in SQL. It returns rows from one or more tables. In its simplest form:

SELECT column1, column2
FROM   table_name
WHERE  some_condition
ORDER BY column1
LIMIT 10;

But here’s the part most tutorials skip: SQL doesn’t run that statement top-to-bottom. The logical order is:

  1. FROM — pick the source table(s)
  2. WHERE — filter rows
  3. GROUP BY — collapse into groups (next lesson)
  4. HAVING — filter groups
  5. SELECT — choose the columns to keep
  6. ORDER BY — sort
  7. LIMIT — keep only N rows

That’s why you can’t use a column alias defined in SELECT inside the WHERE clause: the SELECT hasn’t run yet.

Try it

The schema below has users, products, and orders. Run any query against it.

SQL · SQLite
Ready · ⌘↵ runs
Result
(click Run)

SELECT * returns every column. In real production code, always list columns explicitly — SELECT * is unstable (schema changes silently add/remove columns) and slow (every column is shipped over the wire).

Filtering with WHERE

SQL · SQLite
Ready · ⌘↵ runs
Result
(click Run)

BETWEEN a AND b is inclusive of both ends. Other useful comparisons:

WHERE country IN ('IN', 'US')          -- match any in list
WHERE country NOT IN ('CN')
WHERE name LIKE 'A%'                    -- A and anything after
WHERE name ILIKE 'a%'                   -- case-insensitive (Postgres)
WHERE signup_date IS NULL
WHERE signup_date IS NOT NULL

Counting and aggregating

SQL · SQLite
Ready · ⌘↵ runs
Result
(click Run)

COUNT(*) counts rows. COUNT(column) counts non-NULL values in that column. COUNT(DISTINCT column) counts unique non-NULL values. The difference matters when columns have nulls.

ORDER BY and LIMIT

SQL · SQLite
Ready · ⌘↵ runs
Result
(click Run)

DESC = descending, ASC = ascending (default). You can order by multiple columns: ORDER BY country, signup_date DESC.

Column aliases — the small thing that scales

SQL · SQLite
Ready · ⌘↵ runs
Result
(click Run)

In most dialects, AS is optional but recommended for clarity. Table aliases (FROM users u) are the same idea — they keep multi-table queries short.

Putting it together

SQL · SQLite
Ready · ⌘↵ runs
Result
(click Run)

Quick check

Quick check

0/3 answered
Q1.Why does `SELECT name, COUNT(*) AS c FROM users WHERE c > 5` fail?
Q2.Which `WHERE` clause finds rows where `email` is NULL?
Q3.What's the difference between `COUNT(*)` and `COUNT(email)`?

Finished the lesson?

Mark it complete to track your progress and keep your streak alive. +20 XP

Skip to content