Developer Membuang Waktu Berminggu-minggu untuk Peningkatan Performa 4x yang Tidak Memberikan Keuntungan Nyata Karena Data Benchmark yang Cacat

Tim Komunitas BigGo
Developer Membuang Waktu Berminggu-minggu untuk Peningkatan Performa 4x yang Tidak Memberikan Keuntungan Nyata Karena Data Benchmark yang Cacat

Kisah seorang software engineer tentang optimasi yang salah arah telah memicu diskusi luas tentang pentingnya data benchmark yang realistis dalam pengujian performa. Developer tersebut menghabiskan dua minggu untuk membuat implementasi assembly yang dioptimasi secara manual dan memberikan peningkatan kecepatan 4x yang mengesankan dalam pengujian, namun kemudian menemukan bahwa hal itu tidak memberikan manfaat sama sekali di produksi karena asumsi benchmark yang secara fundamental cacat.

Jebakan Data Acak dalam Pengujian Performa

Masalah inti muncul dari penggunaan angka acak untuk menguji optimasi encoding Varint. Meskipun pendekatan ini tampak logis untuk pengujian komprehensif, hal ini menciptakan skenario yang sama sekali tidak realistis. Angka acak 64-bit secara matematis bias terhadap nilai yang sangat besar - dengan 50% memerlukan maksimum 10 bytes untuk encoding dan hampir semua yang lain membutuhkan 8-9 bytes. Ini berarti benchmark tersebut pada dasarnya menguji skenario performa terburuk algoritma daripada pola penggunaan yang tipikal.

Komunitas telah menyoroti bagaimana hal ini merepresentasikan tantangan yang lebih luas dalam pekerjaan optimasi performa. Menciptakan skenario pengujian yang representatif dan mengimplementasikannya dengan benar dalam microbenchmark adalah tugas yang sangat sulit, dan kegagalan dalam area ini bisa sulit dideteksi sampai waktu yang signifikan telah diinvestasikan.

Varint (Variable-length integer): Metode encoding yang kompak yang menggunakan 1-10 bytes untuk merepresentasikan integer, dengan angka yang lebih kecil memerlukan bytes yang lebih sedikit

Distribusi Ukuran Encoding Varint untuk Angka 64-bit Acak:

  • 50% memerlukan 10 byte (maksimum)
  • ~49,6% memerlukan 9 byte
  • ~0,38% memerlukan 8 byte
  • ~0,003% memerlukan 7 byte
  • ~0,00000000000009% memerlukan 2 byte
  • ~0,0000000000000006% memerlukan 1 byte

Distribusi Data Dunia Nyata Menceritakan Kisah yang Berbeda

Revelasi datang ketika memeriksa data produksi aktual, yang mengungkapkan bahwa angka-angka dunia nyata cenderung secara dramatis lebih kecil daripada yang disarankan data pengujian acak. Melihat sekeliling pada angka-angka sehari-hari - jumlah halaman, nomor referensi, kode produk - sebagian besar muat dengan nyaman dalam hanya dua bytes. Perbedaan fundamental ini menjelaskan mengapa encoding Varint ada sejak awal: untuk menangani secara efisien angka-angka kecil yang mendominasi aplikasi nyata.

Fenomena ini terhubung dengan prinsip matematika yang lebih luas seperti Hukum Benford, yang mengamati bahwa dalam banyak dataset dunia nyata, digit terdepan yang lebih kecil muncul lebih sering daripada yang lebih besar. Ketidaksesuaian antara keacakan matematis dan distribusi data praktis merepresentasikan jebakan umum bagi developer yang mengoptimasi algoritma.

Format Encoding Varint:

  • Angka < 128: 1nnnnnnn (1 byte)
  • Angka < 16,384: 1nnnnnnn 0nnnnnnn (2 byte)
  • Angka < 2,097,152: 1nnnnnnn 1nnnnnnn 0nnnnnnn (3 byte)
  • Integer 32-bit: memerlukan 1-5 byte
  • Integer 64-bit: memerlukan 1-10 byte
  • Digunakan dalam: Google Protobuf , Apache Thrift , WASM , DWARF

Tantangan Benchmarking yang Representatif

Diskusi telah mengungkapkan bahwa bahkan developer berpengalaman pun berjuang dengan menciptakan tes performa yang bermakna. Beberapa organisasi telah mengeksplorasi penggunaan profil data produksi atau menerapkan filter pada data pengguna nyata untuk benchmarking yang lebih akurat, meskipun pendekatan-pendekatan ini menghadapi tantangan praktis mereka sendiri.

Mengidentifikasi skenario penggunaan yang representatif untuk dioptimasi dan kemudian mengimplementasikan skenario tersebut dalam driver tes microbenchmark adalah hal yang sangat sulit untuk dilakukan dengan benar

Kisah ini berfungsi sebagai pengingat bahwa angka benchmark yang mengesankan tidak berarti apa-apa tanpa kondisi pengujian yang realistis. Meskipun pencapaian teknis developer dalam menciptakan algoritma 4x lebih cepat adalah genuine, optimasi tersebut memecahkan masalah yang tidak ada dalam praktik. Pengalaman tersebut pada akhirnya menjadi berharga sebagai proof-of-concept untuk optimasi JIT kustom, meskipun implementasi spesifiknya di-rollback.

Kasus ini menyoroti mengapa optimasi performa yang sukses memerlukan perhatian sebanyak pada metodologi pengukuran seperti pada perbaikan kode aktual. Tanpa data yang representatif, bahkan optimasi yang paling canggih pun bisa menjadi solusi rumit untuk masalah yang tidak ada.

Referensi: That time I wasted weeks hand optimizing assembly because I benchmarked on random data