Saya mencoba menerapkan fungsi berikut dalam floating point presisi ganda dengan kesalahan relatif rendah :
Ini digunakan secara luas dalam aplikasi statistik untuk menambahkan probabilitas atau kepadatan probabilitas yang diwakili dalam ruang log. Tentu saja, baik atau dapat dengan mudah overflow atau underflow, yang akan menjadi buruk karena ruang log digunakan untuk menghindari underflow. Ini adalah solusi khas:
Pembatalan dari memang terjadi, tetapi dikurangi dengan . Lebih buruk lagi adalah ketika dan dekat. Berikut ini plot kesalahan relatif:
Plot dipotong pada untuk menekankan bentuk kurva , tentang pembatalan yang terjadi. Saya telah melihat kesalahan hingga dan menduga bahwa itu menjadi jauh lebih buruk. (FWIW, fungsi "kebenaran dasar" diimplementasikan menggunakan float presisi arbitrer MPFR dengan presisi 128-bit.) l o g s u m ( x , y ) = 0 10 - 11
Saya sudah mencoba reformulasi lain, semuanya dengan hasil yang sama. Dengan sebagai ekspresi luar, kesalahan yang sama terjadi dengan mengambil log sesuatu di dekat 1. Dengan sebagai ekspresi luar, pembatalan terjadi di ekspresi dalam.l o g 1 p
Sekarang, kesalahan absolut sangat kecil, jadi memiliki kesalahan relatif sangat kecil (dalam epsilon). Orang mungkin berpendapat bahwa, karena pengguna benar-benar tertarik pada probabilitas (bukan probabilitas log), kesalahan relatif yang mengerikan ini bukan masalah. Mungkin biasanya tidak, tapi saya sedang menulis fungsi perpustakaan, dan saya ingin kliennya dapat mengandalkan kesalahan relatif tidak lebih buruk daripada kesalahan pembulatan.l o g s u m
Sepertinya saya perlu pendekatan baru. Apa itu?
sumber
Jawaban:
log ∑ i e x i = ξ + log ∑ i e x i - ξ , ξ = maks i x i
Jika logsum sangat dekat dengan nol dan Anda menginginkan akurasi relatif tinggi, Anda mungkin dapat menggunakan menggunakan akurasi (yaitu, lebih dari presisi ganda) implementasi yang hampir linier untuk kecil .l e x p ( z ) : = log ( 1 + e - | z | )
sumber