Ringkasan:
Saya mencari cara tercepat untuk menghitung
(int) x / (int) y
tanpa mendapatkan pengecualian untuk y==0
. Sebaliknya saya hanya menginginkan hasil yang sewenang-wenang.
Latar Belakang:
Saat mengkodekan algoritma pemrosesan gambar, saya sering kali perlu membagi dengan nilai alfa (terakumulasi). Varian paling sederhana adalah kode C biasa dengan aritmatika integer. Masalah saya adalah bahwa saya biasanya mendapatkan kesalahan pembagian dengan nol untuk piksel hasil dengan alpha==0
. Namun ini persis piksel di mana hasilnya tidak masalah sama sekali: Saya tidak peduli dengan nilai warna piksel alpha==0
.
Rincian:
Saya mencari sesuatu seperti:
result = (y==0)? 0 : x/y;
atau
result = x / MAX( y, 1 );
x dan y adalah bilangan bulat positif. Kode tersebut dieksekusi berkali-kali dalam loop bersarang, jadi saya mencari cara untuk menyingkirkan percabangan bersyarat.
Ketika y tidak melebihi kisaran byte, saya senang dengan solusinya
unsigned char kill_zero_table[256] = { 1, 1, 2, 3, 4, 5, 6, 7, [...] 255 };
[...]
result = x / kill_zero_table[y];
Tapi ini jelas tidak berfungsi dengan baik untuk rentang yang lebih besar.
Saya kira pertanyaan terakhirnya adalah: Apa bit twiddling hack tercepat yang mengubah 0 menjadi nilai integer lainnya, sementara membiarkan semua nilai lain tidak berubah?
Klarifikasi
Saya tidak 100% yakin bahwa percabangan itu terlalu mahal. Namun, kompiler yang berbeda digunakan, jadi saya lebih suka melakukan benchmarking dengan sedikit pengoptimalan (yang memang dipertanyakan).
Yang pasti, kompiler sangat bagus dalam hal bit twiddling, tapi saya tidak bisa mengungkapkan hasil "tidak peduli" di C, jadi kompilator tidak akan pernah bisa menggunakan berbagai optimasi lengkap.
Kode harus sepenuhnya kompatibel dengan C, platform utamanya adalah Linux 64 Bit dengan gcc & clang dan MacOS.
y += !y
? Tidak ada cabang yang diperlukan untuk menghitungnya. Anda bisa membandingkan x / (y + !y)
terhadap x / max(y, 1)
dan mungkin juga y ? (x/y) : 0
. Saya kira tidak akan ada cabang di salah satu dari mereka, setidaknya dengan pengoptimalan diaktifkan.
0
sangat besar dan berdekatan. Ada tempat untuk bermain-main dengan pengoptimalan mikro, dan operasi per piksel adalah tempat yang tepat .