ROLLUP dan CUBE di SQL untuk Subtotal (2026)
TL;DR
ROLLUP bikin subtotal hierarkis dari kiri ke kanan plus grand total, cocok buat data bertingkat kayak tahun lalu bulan. CUBE bikin subtotal untuk semua kemungkinan kombinasi kolom sekaligus. Sintaksnya GROUP BY ROLLUP(kolom1, kolom2) atau GROUP BY CUBE(kolom1, kolom2). Keduanya pintasan dari GROUPING SETS dan didukung PostgreSQL, SQL Server, serta Oracle.
ROLLUP bikin subtotal bertingkat plus grand total otomatis, CUBE bikin subtotal untuk semua kombinasi kolom sekaligus. Dua pintasan SQL buat laporan yang butuh angka rangkuman di banyak level.
Kalau kamu sering diminta laporan yang nunjukin total per bulan, subtotal per tahun, dan grand total dalam satu tabel, ROLLUP ngerjain itu semua dalam satu klausa. Nggak perlu query terpisah tiap level.
Di sini kamu bakal lihat sintaks keduanya, beda cara kerjanya, cara nandain baris subtotal, plus contoh laporan penjualan toko.
Apa itu ROLLUP dan CUBE di SQL?
ROLLUP dan CUBE adalah ekstensi GROUP BY buat ngitung subtotal dan grand total dalam satu query. ROLLUP ngasih subtotal hierarkis dari kiri ke kanan. CUBE ngasih subtotal untuk tiap kemungkinan kombinasi kolom.
Keduanya sebenernya pintasan dari GROUPING SETS. Bedanya, ROLLUP dan CUBE nulis pola umum secara ringkas, sementara GROUPING SETS bikin kamu nentuin tiap grup manual.
Fitur ini didukung PostgreSQL, SQL Server, dan Oracle. MySQL cuma punya WITH ROLLUP, nggak ada CUBE.
Gimana cara kerja ROLLUP?
ROLLUP numpuk subtotal dari kolom paling kanan ke kiri. Buat ROLLUP(tahun, bulan), kamu dapat tiga level: detail per tahun-bulan, subtotal per tahun, dan grand total.
SELECT
tahun,
bulan,
SUM(total) AS total_penjualan
FROM penjualan
GROUP BY ROLLUP (tahun, bulan)
ORDER BY tahun, bulan;
Hasilnya kira-kira gini:
| tahun | bulan | total_penjualan |
|---|---|---|
| 2026 | 1 | 12.000.000 |
| 2026 | 2 | 15.000.000 |
| 2026 | NULL | 27.000.000 |
| NULL | NULL | 27.000.000 |
Baris dengan bulan NULL adalah subtotal tahun. Baris dua NULL adalah grand total. Perhatiin ROLLUP nggak ngasih subtotal per bulan lintas tahun. Itu bagian yang cuma bisa dari CUBE.
Gimana cara kerja CUBE?
CUBE bikin subtotal untuk semua kombinasi kolom. Buat CUBE(kota, produk), kamu dapat empat level: per kota-produk, per kota, per produk, dan grand total.
SELECT
kota,
produk,
SUM(total) AS total_penjualan
FROM penjualan
GROUP BY CUBE (kota, produk)
ORDER BY kota, produk;
Bedanya sama ROLLUP: CUBE ngasih subtotal per produk yang berdiri sendiri lintas kota. ROLLUP nggak. Aturan jumlahnya: CUBE menghasilkan 2 pangkat n level, di mana n jumlah kolom. Dua kolom berarti 4 level. Tiga kolom langsung 8 level. Makin banyak kolom, makin banyak baris subtotal.
Gimana nandain baris subtotal?
NULL dari subtotal gampang ketuker sama NULL asli di data. Pakai fungsi GROUPING() buat bedain. Fungsi ini balikin 1 kalau kolomnya lagi di-agregasi, 0 kalau nggak.
SELECT
CASE WHEN GROUPING(tahun) = 1 THEN 'Semua Tahun' ELSE tahun::text END AS tahun,
CASE WHEN GROUPING(bulan) = 1 THEN 'Total' ELSE bulan::text END AS bulan,
SUM(total) AS total_penjualan
FROM penjualan
GROUP BY ROLLUP (tahun, bulan);
Sekarang baris subtotal nunjukin label Total, bukan NULL kosong. Laporan langsung kebaca tanpa perlu dijelasin.
Contoh kasus: laporan tahunan toko_berkah
Toko_berkah mau laporan penjualan yang nunjukin total per bulan, subtotal per tahun, dan grand total, dalam satu tabel. Ini kasus klasik buat ROLLUP karena datanya bertingkat: tahun di atas, bulan di bawah.
SELECT
tahun,
bulan,
SUM(total) AS total_penjualan
FROM penjualan
GROUP BY ROLLUP (tahun, bulan)
ORDER BY tahun, bulan;
Waktu aku pakai ROLLUP di data 24 bulan dengan 890 ribu transaksi, satu query ini ngasih 24 baris detail plus 2 baris subtotal tahun plus 1 grand total, semua dalam sekali jalan. Sebelumnya butuh tiga query terpisah yang digabung, dan tabelnya kebaca tiga kali. ROLLUP baca sekali.
Butuh persen tiap bulan terhadap total tahun? Lanjut pakai window function persen dari total. Buat pengelompokan dasar, pahami dulu konsep GROUP BY. Kalau kamu butuh kombinasi grup yang lebih spesifik, GROUPING SETS lebih pas.
ROLLUP vs CUBE vs GROUPING SETS
Tabel ini bantu kamu milih cepat.
| Fitur | Yang dihasilkan | Kapan dipakai |
|---|---|---|
| ROLLUP | Subtotal hierarkis kiri ke kanan + grand total | Data bertingkat: tahun, bulan, hari |
| CUBE | Semua kombinasi subtotal | Analisis silang penuh antar dimensi |
| GROUPING SETS | Cuma kombinasi yang kamu sebut | Butuh kontrol penuh, grup non-hierarkis |
Kesalahan umum saat pakai ROLLUP dan CUBE
Dua hal ini paling sering bikin hasil kelihatan aneh.
- Salah urutan kolom di ROLLUP. ROLLUP peka urutan.
ROLLUP(tahun, bulan)beda hasil dariROLLUP(bulan, tahun). Taruh kolom level tertinggi di kiri. - Pakai CUBE buat kolom yang banyak. Empat kolom bikin 16 level subtotal. Kalau kamu cuma butuh sebagian, ganti ke GROUPING SETS biar hemat.
Satu catatan: kalau data kamu sendiri punya NULL, GROUPING() jadi satu-satunya cara aman bedain NULL subtotal dari NULL asli.
Penutup
ROLLUP dan CUBE ngubah laporan multi-level jadi satu query ringkas. Yang perlu kamu bawa:
- ROLLUP buat subtotal hierarkis, CUBE buat semua kombinasi.
- CUBE menghasilkan 2 pangkat n level, hati-hati kalau kolomnya banyak.
- Pakai GROUPING() plus CASE buat kasih label baris subtotal.
Mau query agregasi kayak gini jadi kebiasaan? Latihan langsung di NgulikSQL sambil ngerjain data beneran. Referensi sintaks resmi ada di dokumentasi PostgreSQL GROUPING SETS, CUBE, ROLLUP. Lanjut baca conditional aggregation dengan CASE buat naikin level laporanmu.
Mau praktek langsung? Mulai latihan SQL gratis
Latihan interaktif, langsung di browser.
Artikel terkait
Composite Index di SQL: Cara Kerja dan Urutan Kolom
Composite index itu index atas beberapa kolom sekaligus. Urutan kolomnya nentuin query mana yang kebantu, lewat aturan leftmost prefix.
Menghitung Stickiness (DAU/MAU) di SQL
Stickiness ngukur seberapa sering user balik lagi. Ini cara hitung DAU, MAU, dan rasio stickiness pakai SQL, plus contoh aplikasi UMKM.
Menghitung DAU dan MAU dengan SQL
DAU dan MAU dua metrik wajib buat produk digital. Ini cara hitungnya pakai SQL, lengkap query DISTINCT, per bulan, sampai rasio stickiness.