SQL NOT
NOT negates a condition. Combine with =, IN, EXISTS, BETWEEN, LIKE, NULL for clean exclusion logic.
NOT in practice
EXAMPLE
-- NOT with equality
SELECT id FROM users WHERE NOT country = 'AU';
-- Equivalent and more readable:
SELECT id FROM users WHERE country <> 'AU';
-- NOT IN
SELECT id FROM users
WHERE country NOT IN ('AU', 'NZ', 'US');
-- NOT IN gotcha: a NULL inside the list makes EVERY row not match
SELECT id FROM users WHERE country NOT IN ('AU', NULL);
-- Returns ZERO rows (because anything compared to NULL is unknown)
-- Safer: NOT EXISTS
SELECT u.id
FROM users u
WHERE NOT EXISTS (
SELECT 1 FROM bans b WHERE b.user_id = u.id
);
-- NOT LIKE
SELECT email FROM users WHERE email NOT LIKE '%@spammy.com';
-- NOT BETWEEN
SELECT id FROM orders WHERE total NOT BETWEEN 100 AND 500;
-- IS NOT NULL - the only way to test for non-null
SELECT id FROM users WHERE deleted_at IS NOT NULL;
-- Combining with AND/OR
SELECT id, email
FROM users
WHERE active = TRUE
AND NOT (country = 'AU' AND tier = 'free');
-- Equivalent via De Morgan's law
SELECT id, email
FROM users
WHERE active = TRUE
AND (country <> 'AU' OR tier <> 'free');
-- NOT in CHECK constraints
CREATE TABLE orders (
id SERIAL PRIMARY KEY,
total INT NOT NULL CHECK (total >= 0),
status TEXT NOT NULL CHECK (status IN ('open','paid','shipped','cancelled'))
);
-- NOT EXISTS for anti-joins (users with no orders)
SELECT u.id
FROM users u
WHERE NOT EXISTS (
SELECT 1 FROM orders o WHERE o.user_id = u.id
);
Why it matters
Most NOT-bugs come from NULL. Use NOT EXISTS instead of NOT IN whenever the inner set might contain NULL. Prefer <> for equality negation - it reads cleaner than NOT =.
Tip: Tweak the snippet with Try it Yourself », then sit the quiz at the bottom of the page.
Example
Exercise
Find rows where the phone is present (not null).
WHERE phone IS
NULL
Three letters; logical negation.
Discussion
Loading…