Saya bingung mengapa kita peduli dengan representasi yang berbeda untuk nol positif dan negatif.
Samar-samar saya ingat membaca klaim bahwa memiliki representasi nol negatif sangat penting dalam pemrograman yang melibatkan bilangan kompleks. Saya tidak pernah memiliki kesempatan untuk menulis kode yang melibatkan bilangan kompleks, jadi saya sedikit bingung mengapa ini bisa terjadi.
Artikel Wikipedia tentang konsep ini tidak terlalu membantu; itu hanya membuat klaim samar tentang nol ditandatangani membuat operasi matematika tertentu lebih sederhana di floating point, jika saya mengerti dengan benar. Jawaban ini mencantumkan beberapa fungsi yang berperilaku berbeda, dan mungkin sesuatu dapat disimpulkan dari contoh jika Anda terbiasa dengan bagaimana mereka dapat digunakan. (Meskipun, contoh khusus dari akar kuadrat kompleks tampak salah datar, karena kedua angka tersebut secara matematis setara, kecuali saya memiliki kesalahpahaman.) Tetapi saya tidak dapat menemukan pernyataan yang jelas tentang jenis masalah yang akan Anda hadapi jika tidak ada. Semakin banyak sumber daya matematis yang dapat saya temukan menyatakan bahwa tidak ada yang membedakan antara keduanya dari perspektif matematika, dan artikel Wikipedia tampaknya menyarankan bahwa ini jarang terlihat di luar komputasi selain dari menggambarkan batas.
Jadi mengapa nol negatif bernilai dalam komputasi? Saya yakin saya hanya melewatkan sesuatu.
sumber
sqrt(-1+0i) = i
dansqrt(-1-0i) = -i
, meskipun berpakaian dengan sintaks yang tepat untuk beberapa bahasa pemrograman, saya percaya. Saya akan mengedit agar lebih jelas.Jawaban:
Anda harus ingat bahwa dalam FPU arithmetics, 0 tidak harus berarti nol, tetapi juga nilainya terlalu kecil untuk diwakili menggunakan tipe data yang diberikan, misalnya
a terlalu kecil untuk diwakili dengan benar oleh float (32 bit), sehingga "dibulatkan" menjadi -0.
Sekarang, katakanlah perhitungan kita berlanjut:
Karena a adalah float, itu akan menghasilkan -infinity yang cukup jauh dari jawaban yang benar -100000000000000000000.0.0
Sekarang mari kita hitung b jika tidak ada -0 (jadi a dibulatkan menjadi +0):
Hasilnya salah lagi karena pembulatan, tetapi sekarang "lebih salah" - tidak hanya secara numerik, tetapi yang lebih penting karena tanda yang berbeda (hasil perhitungan adalah + tak terhingga, hasil yang benar adalah -100000000000000000000.0.0).
Anda masih bisa mengatakan bahwa itu tidak masalah karena keduanya salah. Yang penting adalah bahwa ada banyak aplikasi numerik di mana hasil paling penting dari perhitungan adalah tanda - misalnya ketika memutuskan apakah akan belok kiri atau kanan di perempatan dengan menggunakan beberapa algoritma pembelajaran mesin, Anda dapat mengartikan nilai positif => belokan kiri, nilai negatif => belok kanan, "besaran" sebenarnya dari nilai tersebut hanyalah "koefisien kepercayaan".
sumber
+inf
dan-inf
dalam operasi normal disadap.+inf
dan-inf
. Jika program Anda menyebabkan floating point underflow, itu adalah bug dan apa yang terjadi sesudahnya tidak begitu menarik, imho. Kami masih kehilangan contoh praktis di mana -0 berguna.Pertama, bagaimana Anda membuat -0? Ada dua cara: (1) melakukan operasi floating-point di mana hasil matematika negatif, tetapi sangat dekat dengan nol sehingga dibulatkan menjadi nol dan bukan ke angka bukan nol. Perhitungan itu akan memberikan -0. (B) Operasi tertentu yang melibatkan nol: Kalikan nol positif dengan angka negatif, atau bagi nol positif dengan angka negatif, atau negasikan nol positif.
Memiliki nol negatif menyederhanakan multiplikasi dan pembagian sedikit, tanda x * y atau x / y selalu merupakan tanda x, eksklusif atau tanda y. Tanpa nol negatif, harus ada beberapa pemeriksaan tambahan untuk mengganti -0 dengan +0.
Ada beberapa situasi yang sangat langka di mana itu berguna. Anda dapat memeriksa apakah hasil dari perkalian atau pembagian secara matematis lebih besar dari atau kurang dari nol, bahkan jika ada underflow (selama Anda tahu hasilnya bukan nol matematika). Saya tidak ingat pernah memiliki kode tertulis di mana itu membuat perbedaan.
Mengoptimalkan kompiler membenci -0. Misalnya, Anda tidak dapat mengganti x + 0,0 dengan x, karena hasilnya tidak boleh x jika x adalah -0,0. Anda tidak dapat mengganti x * 0,0 dengan 0,0, karena hasilnya harus -0,0 jika x <0 atau x adalah -0,0.
sumber
-5
dan5
masukfmod()
. Ini cukup mengganggu untuk kasus penggunaan saya.C # Double yang sesuai dengan IEEE 754
cetakan:
sebenarnya untuk menjelaskan sedikit ...
Ini berarti sesuatu yang jauh lebih dekat dengan d =
The Limit of x as x approaches 0-
atauThe Limit of x as x approaches 0 from the negatives
.Untuk menanggapi komentar Philipp ...
Pada dasarnya nol negatif berarti underflow.
Ada sedikit penggunaan praktis untuk nol negatif jika ...
misalnya, kode ini (lagi C #):
menghasilkan hasil ini:
Untuk menjelaskan secara informal, Semua nilai khusus yang dapat dimiliki oleh floating point IEEE 754 (infinity positif, infinity negatif, NAN, -0.0) tidak memiliki arti dalam arti praktis. Mereka tidak dapat mewakili nilai fisik apa pun, atau nilai apa pun yang masuk akal dalam perhitungan "dunia nyata". Apa yang mereka maksud adalah pada dasarnya ini:
sqrt(-7)
, atau tidak memiliki batas suka0/0
atau sukaPositiveInfinity/PositiveInfinity
sumber
Pertanyaan tentang bagaimana ini berhubungan dengan perhitungan bilangan kompleks benar-benar menjadi inti mengapa kedua +0 dan -0 ada di floating-point. Jika Anda mempelajari Analisis Kompleks sama sekali, Anda dengan cepat menemukan bahwa fungsi kontinu dari Kompleks ke Kompleks biasanya tidak dapat diperlakukan sebagai 'bernilai tunggal' kecuali jika seseorang mengadopsi 'fiksi sopan' bahwa output membentuk apa yang dikenal sebagai 'permukaan Riemann'. Sebagai contoh, logaritma kompleks memberikan setiap input tanpa batas banyak output; ketika Anda 'menghubungkannya' untuk membentuk output yang berkelanjutan, Anda akan berakhir dengan semua bagian nyata yang membentuk permukaan 'pembuka botol tak terbatas' di sekitar titik asal. Kurva kontinu yang melintasi sumbu nyata 'ke bawah dari sisi positif-imajiner' dan kurva lain yang 'membungkus kutub' dan melintasi sumbu nyata '
Sekarang menerapkannya ke program numerik yang menghitung menggunakan floating-point kompleks. Tindakan yang diambil setelah perhitungan yang diberikan mungkin sangat berbeda tergantung pada 'lembar' program mana yang saat ini 'aktif', dan tanda hasil perhitungan terakhir mungkin memberi tahu Anda 'lembar' mana. Sekarang anggaplah hasilnya nol? Ingat, di sini 'nol' benar-benar berarti 'terlalu kecil untuk diwakili dengan benar'. Tetapi jika perhitungan dapat mengatur untuk - menyimpan tanda - (yaitu ingat yang 'lembar') ketika hasilnya nol, maka kode dapat memeriksa tanda dan melakukan tindakan yang tepat bahkan dalam situasi ini.
sumber
Alasannya lebih sederhana dari biasanya
Tentu saja ada banyak peretasan yang terlihat sangat bagus dan bermanfaat (seperti pembulatan ke
-0.0
atau+0.0
tetapi anggap kita memiliki representasi int yang ditandatangani dengan tanda minus / plus di awal (saya tahu itu diselesaikan dengan kode biner U2 dalam bilangan bulat biasanya tetapi menganggap representasi ganda yang kurang kompleks):Bagaimana jika ada angka negatif?
Oke, sesederhana itu. Jadi mari kita wakili 0:
Itu baik juga. Tapi bagaimana dengan itu
1 000
? Apakah harus nomor terlarang? Lebih baik tidak.Jadi mari kita asumsikan ada dua jenis nol:
Nah, itu akan menyederhanakan perhitungan kami dan secara tidak sengaja memberikan beberapa fitur tambahan pembulatan. Jadi
+0
dan-0
datang dari hanya masalah representasi biner.sumber