Saya bingung ketika seorang kolega menunjukkan saya jajaran JavaScript yang memperingatkan 42 ini.
alert(2+ 40);
Dengan cepat ternyata apa yang tampak seperti tanda minus sebenarnya adalah karakter Unicode yang misterius dengan semantik yang berbeda.
Ini membuat saya bertanya-tanya mengapa karakter itu tidak menghasilkan kesalahan sintaksis ketika ekspresi diuraikan. Saya juga ingin tahu apakah ada lebih banyak karakter berperilaku seperti ini.
javascript
unicode
GOTO 0
sumber
sumber
;
, editor cenderung mengubah karakter `` aneh menjadi ruang normal, tetapi jika Anda membatalkan "koreksi otomatis", Anda memiliki perilaku yang sama . Karakter itu memiliki semantik yang sama dengan spasi, bahkan jika itu terlihat seperti tanda hubung atau minus (dalam font biasa).Jawaban:
Karakter itu adalah "OGHAM SPACE MARK" , yang merupakan karakter spasi. Jadi kodenya setara dengan
alert(2+ 40)
.Setiap karakter Unicode di kelas Zs adalah karakter spasi putih di JavaScript , tetapi tampaknya tidak banyak .
Namun, JavaScript juga memungkinkan karakter Unicode di pengidentifikasi , yang memungkinkan Anda menggunakan nama variabel yang menarik seperti
ಠ_ಠ
.sumber
Zs
karakter yang dianggap sebagai ruang kosong dalam JavaScript. Ada lebih banyak lagi: github.com/mathiasbynens/regexpu/blob/…ಠ_ಠ
dapat digunakan sebagai pengidentifikasi di JS: ಠ_ಠಠ
diperlakukan sebagai surat hanyalah akal sehat, karena itu surat. Ini akan menjadi bug yang jelas jikaಠ_ಠ
tidak dapat digunakan sebagai pengidentifikasi.Setelah membaca jawaban lain, saya menulis skrip sederhana untuk menemukan semua karakter Unicode dalam kisaran U + 0000 – U + FFFF yang berperilaku seperti spasi putih. Sepertinya, ada 26 atau 27 dari mereka tergantung pada browser, dengan perbedaan pendapat tentang U + 0085 dan U + FFFE.
Perhatikan bahwa sebagian besar karakter ini hanya terlihat seperti ruang putih biasa.
Tampilkan cuplikan kode
sumber
\p{Default Ignorable Code Point}
, bukan hanya a\p{Noncharacter Code Pount}
. U + 0085 selalu menjadi\p{Whitespace}
titik kode. Yang jahat adalah U + 180E MONGOLIAN VOWEL SEPARATOR, yang "baru-baru ini" kehilangan\p{Whitespace}
propertinya. Perhatikan bahwa\p{Pattern Whitespace}
set jauh lebih kecil, dan properti yang tidak berubah. Tetapi\p{Whitespace}
tidak.FEFF
adalah BOM dan dapat diperlakukan seperti "ruang lebar tanpa putus" dalam teks.FFFE
apakah itu setara endian swapped. Mungkin itulah alasan mengapa beberapa browser memperlakukan sebagai spasi.Tampaknya karakter yang Anda gunakan sebenarnya lebih panjang dari tanda minus sebenarnya (tanda hubung).
Bagian atas adalah apa yang Anda gunakan, bagian bawah adalah tanda minus yang seharusnya. Anda sepertinya sudah tahu itu, jadi sekarang mari kita lihat mengapa Javascript melakukan ini.
Karakter yang Anda gunakan sebenarnya adalah tanda spasi ogham yang merupakan karakter spasi, jadi pada dasarnya diartikan sebagai hal yang sama dengan spasi, yang berarti bahwa pernyataan Anda mirip
alert(2+ 40)
dengan Javascript.Ada karakter lain seperti ini di Javascript. Anda dapat melihat daftar lengkapnya di sini di Wikipedia .
Sesuatu yang menarik yang saya perhatikan dari karakter ini adalah cara Google Chrome (dan kemungkinan peramban lain) mengartikannya di bilah atas halaman.
Itu adalah sebuah blok dengan
1680
bagian dalamnya. Itu sebenarnya nomor unicode untuk tanda ruang ogham. Tampaknya ini hanya mesin saya yang melakukan ini, tetapi ini adalah hal yang aneh.Saya memutuskan untuk mencoba ini dalam bahasa lain untuk melihat apa yang terjadi dan ini adalah hasil yang saya dapatkan.
Bahasa yang tidak berfungsi di:
Python 2 & 3
Rubi
Java (di dalam
main
metode)PHP
C
Pergilah
Perl 5
Bahasa itu berfungsi dalam:
Skema
C # (di dalam
Main()
metode)Perl 6
sumber
sudo apt-get install unicode
Saya kira itu harus melakukan sesuatu dengan fakta bahwa untuk beberapa alasan aneh itu diklasifikasikan sebagai spasi putih:
sumber
unicode
.unicode
oleh Radovan Garabík. Repo yang sesuai ada di github.com/garabik/unicode .' '.codePointAt(0)
di konsol akan menghasilkan 5760. sekarang google 5760 unicode.Sepertinya saya ingat pernah membaca sebuah artikel beberapa waktu lalu tentang mengganti semi-titik dua (U + 003B) yang salah dalam kode seseorang dengan U + 037E yang merupakan tanda tanya Yunani.
Keduanya terlihat sama (sejauh yang saya percaya orang Yunani sendiri menggunakan U + 003B) tetapi artikel ini menyatakan bahwa yang lain tidak akan berfungsi.
Beberapa informasi lebih lanjut tentang ini dari Wikipedia ada di sini: https://en.wikipedia.org/wiki/Question_mark#Greek_question_mark
Dan pertanyaan (tertutup) tentang menggunakan ini sebagai lelucon dari SO itu sendiri. Tidak di tempat saya awalnya membacanya AFAIR: JavaScript Prank / Joke
sumber