Database toko online dari chapter sebelumnya kini berisi enam pelanggan, enam produk, dan sembilan pesanan. Mengambil seluruh isi tabel setiap kali dibutuhkan bukanlah pilihan pada data nyata yang berisi jutaan baris — laporan bulanan tim pemasaran mungkin hanya membutuhkan pelanggan Jakarta, dan tim gudang hanya membutuhkan produk dengan harga di rentang tertentu. Chapter ini membahas dua kemampuan dasar DQL: memilih kolom dengan SELECT dan memfilter baris dengan WHERE. Seluruh query dijalankan terhadap data.db dengan pola koneksi dari chapter Pengenalan SQL.

Memilih Kolom dengan SELECT #

Daftar kolom setelah kata kunci SELECT menentukan kolom apa saja — dan dalam urutan apa — yang dikembalikan ke pemanggil query:

sql
SELECT nama, kota FROM pelanggan

Output yang Dihasilkan:

text
('Budi Santoso', 'Jakarta')
('Siti Rahayu', 'Bandung')
('Dewi Lestari', 'Surabaya')
('Rina Kartika', 'Jakarta')
('Andi Wijaya', None)
('Farhan Pratama', 'Bandung')

Query hanya membawa dua kolom dari empat kolom tabel pelanggan, sehingga data yang tidak diperlukan — seperti id dan tanggal_daftar — tidak ikut ditransfer. Tanda bintang (SELECT *) mengembalikan semua kolom sekaligus dan cocok untuk eksplorasi cepat; pada kode produksi, sebutkan kolom secara eksplisit agar perubahan struktur tabel tidak mengubah hasil query secara diam-diam.

Memfilter Baris dengan WHERE #

Klausa WHERE menyaring baris: hanya baris yang membuat kondisi bernilai benar yang lolos. Operator paling dasar adalah perbandingan kesamaan = dan ketidaksamaan <>:

sql
SELECT nama, harga FROM produk WHERE kategori = 'fashion'

Output yang Dihasilkan:

text
('Kemeja Batik', 250000)
('Dress Summer', 380000)
('Sneakers Klasik', 900000)
sql
SELECT nama, harga FROM produk WHERE harga > 1000000

Output yang Dihasilkan:

text
('Smartphone X1', 3500000)
('Laptop Pro 14', 12500000)

Perbandingan lain yang tersedia: <, <=, >, dan >=. Nilai teks ditulis dalam tanda kutip tunggal, sedangkan angka ditulis langsung tanpa kutip. Satu catatan penting: perbandingan apa pun terhadap NULL tidak menghasilkan nilai benar, sehingga baris dengan NULL tidak pernah lolos filter = maupun <> — perilaku ini dibahas pada bagian IS NULL di bawah.

Membandingkan Sekumpulan Nilai dengan IN dan BETWEEN #

Operator IN memeriksa apakah sebuah nilai termasuk dalam daftar, pengganti rangkaian kondisi OR yang panjang:

sql
SELECT id, tanggal, status FROM pesanan WHERE status IN ('selesai', 'dikirim')

Output yang Dihasilkan:

text
(1, '2024-06-01', 'selesai')
(2, '2024-06-03', 'selesai')
(3, '2024-06-10', 'dikirim')
(4, '2024-06-15', 'selesai')
(7, '2024-07-05', 'selesai')
(9, '2024-07-20', 'selesai')

Operator BETWEEN menyaring rentang inklusif — nilai batas bawah dan batas atas ikut dihitung, setara dengan harga >= 500000 AND harga <= 4000000:

sql
SELECT nama, harga FROM produk WHERE harga BETWEEN 500000 AND 4000000

Output yang Dihasilkan:

text
('Smartphone X1', 3500000)
('TWS Earbuds', 750000)
('Sneakers Klasik', 900000)

Rentang juga bekerja untuk teks dan tanggal karena BETWEEN membandingkan urutan nilai, misalnya tanggal BETWEEN '2024-06-01' AND '2024-06-30' untuk pesanan bulan Juni.

Pencarian Pola dengan LIKE #

Operator LIKE mencocokkan teks terhadap pola. Tanda persen (%) mewakili nol atau lebih karakter apa pun, sedangkan garis bawah (_) mewakili tepat satu karakter:

sql
SELECT nama, harga FROM produk WHERE nama LIKE 's%'

Output yang Dihasilkan:

text
('Smartphone X1', 3500000)
('Sneakers Klasik', 900000)

Pola 's%' cocok untuk nama yang diawali huruf s, dan keduanya cocok meski nama produk diawali huruf kapital. Pola dengan persen di kedua sisi mencari teks di posisi mana pun:

sql
SELECT nama, harga FROM produk WHERE nama LIKE '%dress%'

Output yang Dihasilkan:

text
('Dress Summer', 380000)

Menangani NULL dengan IS NULL #

NULL bukan string kosong dan bukan nol — NULL menyatakan nilai yang tidak tersedia, sehingga NULL tidak bisa diperiksa dengan =. SQL menyediakan predikat khusus:

sql
SELECT nama, tanggal_daftar FROM pelanggan WHERE kota IS NULL

Output yang Dihasilkan:

text
('Andi Wijaya', '2024-05-02')
sql
SELECT nama, kota FROM pelanggan WHERE kota IS NOT NULL

Output yang Dihasilkan:

text
('Budi Santoso', 'Jakarta')
('Siti Rahayu', 'Bandung')
('Dewi Lestari', 'Surabaya')
('Rina Kartika', 'Jakarta')
('Farhan Pratama', 'Bandung')

Menggabungkan Kondisi dengan AND, OR, dan NOT #

Kondisi-kondisi dapat digabungkan: AND menuntut semua kondisi benar, OR cukup salah satu, dan NOT membalik hasil sebuah kondisi:

sql
SELECT nama, harga FROM produk
WHERE kategori = 'fashion' AND harga > 300000

Output yang Dihasilkan:

text
('Dress Summer', 380000)
('Sneakers Klasik', 900000)
sql
SELECT nama, kategori, harga FROM produk
WHERE kategori = 'elektronik' OR harga > 800000

Output yang Dihasilkan:

text
('Smartphone X1', 'elektronik', 3500000)
('Laptop Pro 14', 'elektronik', 12500000)
('TWS Earbuds', 'elektronik', 750000)
('Sneakers Klasik', 'fashion', 900000)

Operator AND diikat lebih kuat daripada OR, mirip perkalian terhadap penjumlahan. Sneakers Klasik lolos pada query kedua karena harga > 800000 terpenuhi meskipun kategorinya fashion. Ketika logika mulai bersarang — misalnya (a OR b) AND c — bungkus setiap kelompok kondisi dengan tanda kurung agar urutan pengecekan eksplisit. Terakhir, NOT membalik hasil kondisi:

sql
SELECT id, status FROM pesanan WHERE NOT status = 'selesai'

Output yang Dihasilkan:

text
(3, 'dikirim')
(5, 'dibatalkan')
(6, 'diproses')
(8, 'diproses')

Kita kini mampu mengambil kolom dan baris yang tepat, tetapi hasil query masih tampil dalam urutan penyimpanan tabel. Laporan yang rapi — misalnya produk termahal di posisi teratas atau sepuluh pelanggan terbaru — membutuhkan pengurutan dan pembatasan hasil, materi chapter Sorting dan Limiting. Rujukan sintaks SELECT dan WHERE: SQLite dan PostgreSQL .