Saya ingin melihat bilangan bulat, positif atau negatif, dalam biner.
Agak suka pertanyaan ini , tapi untuk JavaScript.
javascript
numbers
barlop
sumber
sumber
Jawaban:
Anda dapat menggunakan
Number.toString(2)
fungsi, tetapi memiliki beberapa masalah saat merepresentasikan angka negatif. Misalnya,(-1).toString(2)
output"-1"
.Untuk memperbaiki masalah ini, Anda dapat menggunakan operator bitwise pergeseran kanan yang tidak ditandatangani (
>>>
) untuk memaksa nomor Anda ke integer yang tidak ditandatangani.Jika Anda menjalankan,
(-1 >>> 0).toString(2)
Anda akan menggeser angka 0 bit Anda ke kanan, yang tidak mengubah angka itu sendiri tetapi akan diwakili sebagai bilangan bulat yang tidak ditandatangani. Kode di atas akan menampilkan"11111111111111111111111111111111"
dengan benar.Pertanyaan ini memiliki penjelasan lebih lanjut.
sumber
Mencoba
2 adalah radix dan dapat berupa basis antara 2 dan 36
sumber di sini
MEMPERBARUI:
Ini hanya akan berfungsi untuk angka positif, Javascript mewakili bilangan bulat biner negatif dalam notasi dua komplemen. Saya membuat fungsi kecil ini yang seharusnya melakukan trik, saya belum mengujinya dengan benar:
Saya mendapat bantuan dari sini
sumber
-3
pengembalian1
). Saya juga percayadec > 0
harusdec >= 0
, yang setidaknya harus memperbaiki 0. Karenadec2Bin(0)
pengembalian10
.Biner dalam 'convert to binary' dapat merujuk pada tiga hal utama. Sistem angka posisi, representasi biner dalam memori atau bitstring 32bit. (untuk 64 bit bitstring lihat jawaban Patrick Roberts )
1. Sistem Angka
(123456).toString(2)
akan mengonversi angka ke sistem angka posisi dasar 2 . Dalam sistem ini angka negatif ditulis dengan tanda minus seperti dalam desimal.2. Representasi Internal
Representasi internal angka adalah floating point 64 bit dan beberapa batasan dibahas dalam jawaban ini . Tidak ada cara mudah untuk membuat representasi bit-string ini dalam javascript atau mengakses bit tertentu.
3. Operator Masker & Bitwise
MDN memiliki tinjauan yang baik tentang bagaimana operator bitwise bekerja. Penting:
Sebelum operasi diterapkan, angka floating point 64 bit dilemparkan ke bilangan bulat bertanda 32 bit. Setelah mereka bertobat kembali.
Berikut adalah contoh kode MDN untuk mengubah angka menjadi string 32-bit.
sumber
Cara sederhana hanya ...
sumber
(42).toString(2)
42..toString(2)
1.
yang sama dengan1.0
atau hanya1
(dan Anda juga dapat menghilangkan bagian sebelumnya dan menulis.5
bukan0.5
). Jadi dalam contoh titik pertama adalah pemisah desimal yang merupakan bagian dari angka dan titik kedua adalah operator titik untuk memanggil metode pada nomor itu. Anda harus menggunakan dua titik (atau membungkus angka dalam tanda kurung) dan tidak bisa hanya menulis42.toString(2)
karena parser melihat titik sebagai pemisah desimal dan melempar kesalahan karena operator titik yang hilang.Jawaban ini mencoba menangani input dengan nilai absolut di kisaran 2147483648 10 (2 31 ) - 9007199254740991 10 (2 53 -1).
Dalam JavaScript, angka disimpan dalam representasi titik mengambang 64-bit , tetapi operasi bitwise memaksa mereka ke bilangan bulat 32-bit dalam format komplemen dua , sehingga pendekatan apa pun yang menggunakan operasi bitwise membatasi rentang output ke -2147483648 10 (-2 31 ) - 2147483647 10 (2 31 -1).
Namun, jika operasi bitwise dihindari dan representasi floating point 64-bit dipertahankan dengan hanya menggunakan operasi matematika, kita dapat secara andal mengonversi bilangan bulat aman apa pun ke notasi biner komplemen 64-bit dua dengan menandatangani perpanjangan 53-bit
twosComplement
:Untuk browser lama, polyfill ada untuk fungsi dan nilai berikut:
Number.isSafeInteger()
Number.isInteger()
Number.MAX_SAFE_INTEGER
String.prototype.padStart()
Sebagai bonus tambahan, Anda dapat mendukung semua radix (2–36) jika Anda melakukan konversi komplemen keduanya untuk angka negatif di ⌈64 / log 2 (radix) ⌉ digit dengan menggunakan
BigInt
:Jika Anda tertarik dengan jawaban lama saya yang menggunakan a
ArrayBuffer
untuk membuat gabungan antara aFloat64Array
dan aUint16Array
, silakan merujuk ke riwayat revisi jawaban ini .sumber
-(2**53)-1
untuk2**53-1
bukan hanya-(2**31)
untuk2**31-1
seperti jawaban annan ini.Solusi yang saya gunakan untuk 32-bit, adalah kode akhir dari jawaban ini, yaitu dari developer.mozilla.org (MDN), tetapi dengan beberapa baris ditambahkan untuk A) pemformatan dan B) memeriksa bahwa nomor dalam jangkauan.
Beberapa menyarankan
x.toString(2)
yang tidak bekerja untuk negatif, itu hanya menempel tanda minus di sana untuk mereka, yang tidak baik.Fernando menyebutkan solusi sederhana
(x>>>0).toString(2);
yang baik untuk negatif, tetapi memiliki sedikit masalah ketika x positif. Ini memiliki output dimulai dengan 1, yang untuk bilangan positif tidak melengkapi 2s tepat.Siapa pun yang tidak memahami fakta angka positif dimulai dengan 0 dan angka negatif dengan 1, dalam komplemen 2s, dapat memeriksa SO QnA ini pada komplemen 2s. Apa itu "Komplemen 2"?
Sebuah solusi dapat melibatkan menambahkan 0 untuk angka positif, yang saya lakukan dalam revisi sebelumnya dari jawaban ini. Dan seseorang dapat menerima kadang-kadang memiliki nomor 33bit, atau seseorang dapat memastikan bahwa nomor yang dikonversi berada dalam kisaran - (2 ^ 31) <= x <2 ^ 31-1. Jadi jumlahnya selalu 32 bit. Tapi daripada melakukannya, Anda bisa menggunakan solusi ini di mozilla.org
Jawaban dan kode Patrick panjang dan tampaknya berfungsi untuk 64-bit, tetapi memiliki bug yang ditemukan oleh seorang komentator, dan komentator memperbaiki bug patrick, tetapi patrick memiliki beberapa "angka ajaib" dalam kode yang tidak dikomentari dan memiliki dilupakan dan patrick tidak lagi sepenuhnya memahami kodenya sendiri / mengapa itu bekerja.
Annan memiliki beberapa terminologi yang salah dan tidak jelas tetapi menyebutkan solusi oleh developer.mozilla.org https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Bitwise_Operators Ini berfungsi untuk angka 32-bit.
Kode ini cukup kompak, fungsi dari tiga baris.
Tapi saya telah menambahkan regex untuk memformat output dalam kelompok 8 bit. Berdasarkan Cara mencetak angka dengan koma sebagai ribuan pemisah dalam JavaScript (Saya baru saja mengubahnya dari mengelompokkannya menjadi 3s ke kanan dan menambahkan koma , menjadi pengelompokan dalam 8s dari kanan ke kiri, dan menambahkan spasi )
Dan, sementara mozilla membuat komentar tentang ukuran nMask (jumlah yang dimasukkan) .. bahwa itu harus dalam jangkauan, mereka tidak menguji atau melempar kesalahan ketika jumlahnya di luar jangkauan, jadi saya sudah menambahkan itu.
Saya tidak yakin mengapa mereka menamai parameter mereka 'nMask' tetapi saya akan membiarkannya apa adanya.
Referensi: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Bitwise_Operators
sumber
Anda dapat menulis fungsi Anda sendiri yang mengembalikan array bit. Contoh cara mengonversi angka menjadi bit
Pembagi | Dividen | bit / sisa
2 | 9 | 1
2 | 4 | 0
2 | 2 | 0
~ | 1 | ~
contoh baris di atas: 2 * 4 = 8 dan sisanya adalah 1 jadi 9 = 1 0 0 1
Baca sisa dari bawah ke atas. Angka 1 di tengah ke atas.
sumber
Math.floor(number%2)
bukannumber = Math.floor(number/2)
?Saya menggunakan pendekatan yang berbeda untuk menghasilkan sesuatu yang melakukan ini. Saya memutuskan untuk tidak menggunakan kode ini dalam proyek saya, tetapi saya pikir saya akan meninggalkannya di tempat yang relevan jika berguna bagi seseorang.
sumber
Satu lagi alternatif
sumber
Ini kode saya:
sumber
Ini solusinya. Sebenarnya cukup sederhana
sumber