Menghitung Persen dari Total dengan Window Function SQL
TL;DR
Buat hitung persen dari total di SQL, bagi nilai tiap baris dengan SUM() OVER(). Window function ini ngitung total tanpa nge-collapse baris, jadi tiap baris tetap kelihatan lengkap plus kolom kontribusinya. Tambah PARTITION BY kalau mau persen di dalam tiap grup, misalnya per kategori.
Buat hitung persen dari total di SQL, bagi nilai tiap baris dengan SUM(...) OVER (). Window function ini ngasih total keseluruhan di samping tiap baris, tanpa nge-grup datanya.
Ini pertanyaan bisnis yang muncul terus. Produk ini nyumbang berapa persen ke omzet? Cabang ini porsinya berapa? Sebelum window function, orang bikin subquery atau JOIN ke total. Sekarang cukup satu baris rumus.
Di sini kamu bakal belajar pola dasarnya, cara bikin persen per kategori pakai PARTITION BY, sampai kesalahan yang sering bikin hasilnya meleset.
Apa itu persen dari total dan kenapa pakai window function?
Persen dari total itu kontribusi tiap baris terhadap keseluruhan, dihitung sebagai nilai baris dibagi total semua baris, dikali 100. Window function SUM() OVER() bikin ini gampang karena total dihitung tanpa nge-collapse baris. Data detail tetap utuh, kolom persen nempel di sampingnya.
Kalau pakai GROUP BY biasa, kamu kehilangan baris detail karena datanya udah diringkas. Window function ngejaga tiap baris tetap ada. Itu yang bikin dia pas buat kasus ini.
Gimana rumus dasar persen dari total di SQL?
Pola intinya begini. Anggap ada tabel penjualan dengan kolom produk dan total.
SELECT
produk,
total,
ROUND(total * 100.0 / SUM(total) OVER (), 2) AS persen_dari_total
FROM penjualan
ORDER BY persen_dari_total DESC;
Tiga bagian yang perlu kamu paham:
SUM(total) OVER (): jumlah semua nilai total. Kurung kosong artinya window-nya seluruh tabel.* 100.0: kali 100 buat jadiin persen. Pakai100.0(ada titik) biar hasilnya desimal, bukan pembagian bilangan bulat.ROUND(..., 2): rapiin jadi 2 angka di belakang koma.
Hasilnya: tiap produk punya kolom persen, dan kalau dijumlah semua persen mendekati 100. Konsep window function ini sama fondasinya kayak yang dipakai di analisis Pareto 80/20.
Cara hitung persen dari total per kategori (PARTITION BY)
Sering kamu ga mau persen terhadap seluruh tabel, tapi terhadap grupnya sendiri. Misalnya, tiap produk nyumbang berapa persen di dalam kategorinya. Di sinilah PARTITION BY masuk.
SELECT
kategori,
produk,
total,
ROUND(
total * 100.0 / SUM(total) OVER (PARTITION BY kategori),
2
) AS persen_dalam_kategori
FROM penjualan
ORDER BY kategori, persen_dalam_kategori DESC;
PARTITION BY kategori bikin total dihitung ulang buat tiap kategori. Jadi persen Minuman dijumlah pas 100 sendiri, Makanan juga 100 sendiri. Ini beda sama OVER () kosong yang totalnya satu buat semua baris.
Bandingin dua jenis window
| Window | Total dihitung terhadap | Kapan dipakai |
|---|---|---|
OVER () | Seluruh tabel | Kontribusi ke omzet total |
OVER (PARTITION BY kategori) | Tiap kategori | Kontribusi di dalam kategori |
Contoh kasus: toko_berkah
Di dataset toko_berkah ngulikdata, ada 6 kategori produk dengan total 14.880 transaksi setahun. Manajer mau tau kategori mana yang paling nyumbang ke omzet.
SELECT
kategori,
SUM(total) AS omzet,
ROUND(SUM(total) * 100.0 / SUM(SUM(total)) OVER (), 2) AS persen
FROM transaksi
GROUP BY kategori
ORDER BY omzet DESC;
Perhatiin SUM(SUM(total)) OVER (). Yang di dalam itu agregasi per kategori, yang di luar itu window buat total semua kategori. Kombinasi ini valid karena window function dijalanin setelah GROUP BY.
Dari dataset itu, kategori Minuman keluar di angka 31,4% dari omzet, disusul Makanan Ringan 22,8%. Dua kategori teratas doang udah nyaris 54% omzet. Angka kayak gini yang bikin keputusan stok jadi lebih terarah.
Kalau kamu mau lihat kontribusi antar waktu, gabungin sama teknik YTD, QTD, dan MTD.
Kesalahan umum
- Integer division. Nulis
total * 100 / SUM(total) OVER ()di database yang total-nya integer bikin hasilnya 0 atau kepotong. Selalu pakai100.0atau CAST ke desimal. - Lupa PARTITION BY. Kalau kamu mau persen per grup tapi nulis
OVER ()kosong, semua baris kebagi total keseluruhan. Persennya jadi kecil-kecil dan ga jumlah 100 per grup. - Nyampur WHERE dan window. WHERE difilter duluan sebelum window dihitung. Jadi total dari
SUM() OVER ()cuma dari baris yang lolos filter, bukan seluruh tabel. Ini sering bikin kaget. - Salah kira window nge-collapse baris. Window function ga ngurangin jumlah baris. Kalau kamu butuh ringkasan, tetap perlu GROUP BY.
FAQ
Apa beda SUM() OVER() dan GROUP BY buat persen?
GROUP BY ngeringkas data jadi satu baris per grup, jadi kamu kehilangan detail. SUM() OVER() ngitung total tanpa nge-collapse baris, jadi tiap baris asli tetap kelihatan plus kolom persennya. Kalau kamu butuh persen di level detail transaksi, pakai window function. Kalau cukup di level ringkasan, GROUP BY aja.
Kenapa hasil persen aku jadi 0 semua?
Itu efek integer division. Kalau kolom nilainya bertipe integer, pembagian di SQL bakal buang angka desimalnya, jadi hasilnya kepotong ke 0. Perbaikin dengan kali 100.0 yang ada titik desimalnya, atau CAST kolomnya jadi numeric dulu sebelum dibagi.
Apakah window function ada di semua database?
Hampir semua yang modern ada: PostgreSQL, MySQL 8, SQL Server, BigQuery, dan Snowflake dukung window function. MySQL versi 5.7 ke bawah nggak dukung, jadi kamu harus pakai subquery buat totalnya. Cek versi database kamu dulu kalau ragu.
Gimana caranya total persen pas 100?
Selama ga ada filter yang misah antara pembilang dan penyebut, jumlah semua persen bakal mendekati 100. Sedikit meleset (misal 99,99) biasanya gara-gara pembulatan ROUND. Kalau butuh pas 100, jangan bulatin dulu di tiap baris, atau sesuaikan baris terakhir secara manual.
Penutup
Persen dari total di SQL cukup satu pola: bagi nilai baris dengan SUM() OVER (). Tambah PARTITION BY kalau mau persen di dalam grup, dan selalu pakai 100.0 biar ga kena integer division.
Window function bikin kamu jawab pertanyaan kontribusi tanpa subquery yang berlapis. Sekali paham polanya, kepakai di mana-mana.
Mau latihan window function langsung di browser tanpa install apa-apa? Coba NgulikSQL, lanjut baca Pareto Analysis dengan SQL. Referensi resmi ada di dokumentasi window function PostgreSQL.
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.