SQL Basics Explained — Complete Beginner's Guide
SQL (Structured Query Language) is the standard language for managing and querying relational databases, enabling you to create, read, update, and delete data stored in tables.
What You’ll Learn
By the end of this tutorial, you’ll write SQL queries using SELECT, INSERT, UPDATE, DELETE, and WHERE clauses, understand filtering and sorting, and work with real database tables hands-on.
Why SQL Basics Matters
SQL is the most widely used database language in the world. Every major application — from social media platforms to banking systems to DodaZIP’s cloud storage — relies on SQL for data storage and retrieval. Learning SQL opens doors to backend development, data analysis, and database administration.
SQL Learning Path
flowchart LR
A[SQL Basics] --> B[MySQL]
B --> C[PostgreSQL]
C --> D[MongoDB]
D --> E[Redis]
E --> F[Database Design]
A --> G{You Are Here}
style G fill:#f90,color:#fff
What Is SQL? (The “Why” First)
Think of a database like a digital filing cabinet. Without SQL, you’d have to rummage through every drawer manually. SQL is the language you speak to the filing clerk — you say “find me all customers from New York who ordered last month,” and the clerk brings you exactly those records.
What You Can Do with SQL
| Operation | SQL Command | Analogy |
|---|---|---|
| Read | SELECT | Ask the clerk for specific files |
| Create | INSERT | Add a new file to the cabinet |
| Update | UPDATE | Change information in a file |
| Delete | DELETE | Remove a file from the cabinet |
These four operations are called CRUD (Create, Read, Update, Delete) — the foundation of all data management.
Your First Database
Let’s create a database and a table to work with. We’ll use a users table — something every application has:
-- Create a table to store user information
CREATE TABLE users (
id INTEGER PRIMARY KEY,
first_name TEXT NOT NULL,
last_name TEXT NOT NULL,
email TEXT UNIQUE NOT NULL,
age INTEGER,
city TEXT,
created_at TEXT DEFAULT CURRENT_TIMESTAMP
);
-- Insert some sample data
INSERT INTO users (first_name, last_name, email, age, city)
VALUES
('Alice', 'Johnson', 'alice@example.com', 28, 'New York'),
('Bob', 'Smith', 'bob@example.com', 35, 'Los Angeles'),
('Charlie', 'Brown', 'charlie@example.com', 22, 'Chicago'),
('Diana', 'Prince', 'diana@example.com', 30, 'New York'),
('Eve', 'Davis', 'eve@example.com', 45, 'Miami');Explanation:
CREATE TABLE users— creates a new table named “users”id INTEGER PRIMARY KEY— each user gets a unique ID (the primary key)TEXT NOT NULL— the field must have a value (can’t be empty)UNIQUE— no two users can have the same emailDEFAULT CURRENT_TIMESTAMP— automatically sets the creation date- The
INSERTstatement adds 5 rows of sample data
SELECT — Reading Data
SELECT is the most common SQL command. It retrieves data from tables.
Select All Columns
-- Get everything from the users table
SELECT * FROM users;Output:
id | first_name | last_name | email | age | city | created_at
1 | Alice | Johnson | alice@example.com | 28 | New York | 2026-06-06
2 | Bob | Smith | bob@example.com | 35 | Los Angeles | 2026-06-06
3 | Charlie | Brown | charlie@example.com| 22 | Chicago | 2026-06-06
4 | Diana | Prince | diana@example.com | 30 | New York | 2026-06-06
5 | Eve | Davis | eve@example.com | 45 | Miami | 2026-06-06Select Specific Columns
-- Only get names and emails
SELECT first_name, last_name, email FROM users;Output:
first_name | last_name | email
Alice | Johnson | alice@example.com
Bob | Smith | bob@example.com
Charlie | Brown | charlie@example.com
Diana | Prince | diana@example.com
Eve | Davis | eve@example.comFilter with WHERE
WHERE is how you narrow down results — like telling the clerk “only from this drawer”:
-- Find all users from New York
SELECT first_name, last_name, city
FROM users
WHERE city = 'New York';Output:
first_name | last_name | city
Alice | Johnson | New York
Diana | Prince | New YorkComparison Operators in WHERE
-- Users over 30
SELECT first_name, last_name, age FROM users WHERE age > 30;
-- Users 25 to 35
SELECT first_name, last_name, age FROM users WHERE age BETWEEN 25 AND 35;
-- Multiple conditions
SELECT first_name, last_name, city, age
FROM users
WHERE (city = 'New York' OR city = 'Chicago') AND age < 35;Output (age > 30):
first_name | last_name | age
Bob | Smith | 35
Diana | Prince | 30
Eve | Davis | 45Sorting with ORDER BY
-- Sort by age, youngest first
SELECT first_name, last_name, age
FROM users
ORDER BY age ASC;
-- Sort by age, oldest first
SELECT first_name, last_name, age
FROM users
ORDER BY age DESC;Output (ASC):
first_name | last_name | age
Charlie | Brown | 22
Alice | Johnson | 28
Diana | Prince | 30
Bob | Smith | 35
Eve | Davis | 45Limiting Results
-- Get the 3 oldest users
SELECT first_name, last_name, age
FROM users
ORDER BY age DESC
LIMIT 3;Output:
first_name | last_name | age
Eve | Davis | 45
Bob | Smith | 35
Diana | Prince | 30INSERT — Adding New Data
-- Add a single user
INSERT INTO users (first_name, last_name, email, age, city)
VALUES ('Frank', 'Wilson', 'frank@example.com', 29, 'Seattle');
-- Add multiple users at once
INSERT INTO users (first_name, last_name, email, age, city)
VALUES
('Grace', 'Lee', 'grace@example.com', 27, 'Boston'),
('Henry', 'Taylor', 'henry@example.com', 33, 'Austin');UPDATE — Modifying Existing Data
Always use WHERE with UPDATE! Without it, you’ll update every row:
-- CORRECT: Update only Charlie's city
UPDATE users
SET city = 'San Francisco'
WHERE first_name = 'Charlie' AND last_name = 'Brown';
-- Check the result
SELECT first_name, last_name, city FROM users WHERE id = 3;Output:
first_name | last_name | city
Charlie | Brown | San FranciscoUpdating Multiple Columns
-- Diana moved and had a birthday
UPDATE users
SET city = 'Washington DC', age = 31
WHERE id = 4;DELETE — Removing Data
Always use WHERE with DELETE! Without it, you delete everything:
-- Delete a specific user
DELETE FROM users WHERE id = 5;
-- Delete all users from a city
DELETE FROM users WHERE city = 'Miami';
-- Check remaining users
SELECT first_name, last_name FROM users;Output:
first_name | last_name
Alice | Johnson
Bob | Smith
Charlie | Brown
Diana | Prince
Frank | Wilson
Grace | Lee
Henry | TaylorPutting It All Together — Real-World Querying
Here’s how you’d query user data in a real application:
-- Find active users in New York, ordered by when they joined
SELECT first_name, last_name, email, created_at
FROM users
WHERE city = 'New York' AND age >= 18
ORDER BY created_at DESC;
-- Count users per city
SELECT city, COUNT(*) as user_count
FROM users
GROUP BY city
ORDER BY user_count DESC;Output (GROUP BY):
city | user_count
New York | 2
Los Angeles | 1
Chicago | 1
Seattle | 1
Boston | 1
Austin | 1Common SQL Mistakes
1. Forgetting the WHERE Clause on UPDATE/DELETE
-- DANGER: This updates EVERY user's city!
UPDATE users SET city = 'Unknown';
-- DANGER: This deletes EVERY user!
DELETE FROM users;Always run SELECT * FROM table WHERE condition first to preview what your UPDATE/DELETE will affect.
2. Comparing NULL with =
NULL is not a value — it’s the absence of a value. Use IS NULL or IS NOT NULL:
-- WRONG: won't find any rows
SELECT * FROM users WHERE city = NULL;
-- CORRECT
SELECT * FROM users WHERE city IS NULL;3. Mixing Single and Double Quotes
SQL uses single quotes for strings. Double quotes are for identifiers (table/column names) in some databases:
-- CORRECT
SELECT * FROM users WHERE city = 'New York';
-- WRONG (in most databases)
SELECT * FROM users WHERE city = "New York";4. Not Using Primary Keys
Every table should have a primary key. Without one, you can’t uniquely identify rows, and UPDATE/DELETE becomes dangerous.
5. Forgetting Semicolons
SQL statements end with semicolons. Most tools accept statements without them, but it’s a good habit.
6. SELECT * in Production
SELECT * returns all columns. In production queries, list only the columns you need. This improves performance and reduces data transfer.
7. Not Using Transactions for Multiple Operations
When performing multiple related writes, use transactions so all succeed or all fail together:
BEGIN TRANSACTION;
UPDATE accounts SET balance = balance - 100 WHERE id = 1;
UPDATE accounts SET balance = balance + 100 WHERE id = 2;
COMMIT;Common Mistakes Beginners Make
1. Skipping the Fundamentals
Many beginners jump straight to advanced topics without mastering the basics. Take time to understand the core concepts before moving on.
2. Not Practicing Enough
Reading tutorials without writing code leads to shallow understanding. Code along with every example and experiment on your own.
3. Ignoring Error Messages
Error messages tell you exactly what went wrong. Read them carefully — they usually point to the line and type of issue.
4. Copy-Pasting Without Understanding
It’s tempting to copy code from tutorials, but typing it yourself and understanding each line builds real skill.
5. Giving Up Too Early
Every developer hits frustrating bugs. Take breaks, ask for help, and remember that struggling is part of learning.
Practice Questions
1. What does CRUD stand for?
Create, Read, Update, Delete — the four basic operations for managing data.
2. What’s the difference between WHERE and HAVING?
WHERE filters rows before grouping (GROUP BY). HAVING filters groups after grouping. Use WHERE for individual row conditions, HAVING for aggregate conditions.
3. Why should you always use WHERE with DELETE?
Without WHERE, DELETE removes ALL rows from the table. Always run SELECT with the same WHERE clause first to preview.
4. What does ORDER BY age DESC LIMIT 3 do?
Returns the 3 rows with the highest age values, sorted from oldest to youngest.
5. Challenge: Write a query that finds all users whose names start with ‘A’ and are over 25, sorted by age.
SELECT first_name, last_name, age
FROM users
WHERE first_name LIKE 'A%' AND age > 25
ORDER BY age;Real-World Task: Analyze a Dataset
Using the users table, run these analytical queries:
-- Average age per city
SELECT city, AVG(age) as avg_age, COUNT(*) as count
FROM users
GROUP BY city;
-- Users created in the last 7 days
SELECT * FROM users
WHERE created_at >= DATE('now', '-7 days');
-- Find potential duplicates (same city and similar age)
SELECT city, age, COUNT(*) as count
FROM users
GROUP BY city, age
HAVING count > 1;FAQ
Try It Yourself
Run all the examples above using SQLite (comes pre-installed on macOS/Linux, or download for Windows):
# Create a database and run SQL commands
sqlite3 test.db
-- Inside SQLite, paste the CREATE TABLE and INSERT statements,
-- then try your own queries# Or use Python to interact with SQLite
import sqlite3
conn = sqlite3.connect(":memory:")
cursor = conn.cursor()
# Create table
cursor.execute("""
CREATE TABLE users (
id INTEGER PRIMARY KEY,
first_name TEXT NOT NULL,
last_name TEXT NOT NULL,
email TEXT UNIQUE NOT NULL,
age INTEGER,
city TEXT
)
""")
# Insert data
users = [
("Alice", "Johnson", "alice@example.com", 28, "New York"),
("Bob", "Smith", "bob@example.com", 35, "Los Angeles"),
("Charlie", "Brown", "charlie@example.com", 22, "Chicago"),
]
cursor.executemany(
"INSERT INTO users (first_name, last_name, email, age, city) VALUES (?, ?, ?, ?, ?)",
users
)
conn.commit()
# Query
cursor.execute("SELECT first_name, last_name, age FROM users WHERE age > 25")
print("Users over 25:")
for row in cursor.fetchall():
print(f" {row[0]} {row[1]} ({row[2]} years old)")
conn.close()Expected output:
Users over 25:
Alice Johnson (28 years old)
Bob Smith (35 years old)This is the same kind of querying that powers applications like DodaZIP’s file management API and Durga Antivirus Pro’s threat database.
What’s Next
What’s Next
Congratulations on completing this Sql Basics tutorial! Here’s where to go from here:
- Practice daily — Consistency is more important than long study sessions
- Build a project — Apply what you learned by building something real
- Explore related topics — Check out other tutorials in the same category
- Join the community — Discuss with other learners and share your progress
Remember: every expert was once a beginner. Keep coding!
Built by the developers of DodaTech
Doda Browser, DodaZIP & Durga Antivirus Pro