Ci sono caratteri invisibili qui che alterano la modalità di visualizzazione del codice. In Intellij questi possono essere trovati copiando e incollando il codice in una stringa vuota ( ""
), che li sostituisce con escape Unicode, rimuovendo i loro effetti e rivelando l'ordine che il compilatore vede.
Ecco l'output di quel copia-incolla:
"class M\u202E{public static void main(String[]a\u202D){System.out.print(new char[]\n"+
"{'H','e','l','l','o',' ','W','o','r','l','d','!'});}} "
I caratteri del codice sorgente sono memorizzati in questo ordine e il compilatore li considera come in questo ordine, ma sono visualizzati in modo diverso.
Nota il \u202E
carattere, che è un override da destra a sinistra, che inizia un blocco in cui tutti i personaggi sono obbligati a essere visualizzati da destra a sinistra e il \u202D
, che è un override da sinistra a destra, iniziando un blocco nidificato in cui tutti i personaggi vengono forzati nell'ordine da sinistra a destra, sovrascrivendo la prima sostituzione.
Ergo, quando visualizza il codice originale, class M
viene visualizzato normalmente, ma \u202E
inverte l'ordine di visualizzazione di tutto da lì a \u202D
, che inverte di nuovo tutto. (Formalmente, tutto dalla \u202D
terminazione alla riga viene invertito due volte, una volta a causa della \u202D
e una volta con il resto del testo invertito a causa della \u202E
, motivo per cui questo testo appare al centro della riga anziché alla fine.) La direzionalità della riga successiva viene gestita indipendentemente dalla prima a causa del terminatore di linea, quindi {'H','e','l','l','o',' ','W','o','r','l','d','!'});}}
viene visualizzata normalmente.
Per l'algoritmo bidirezionale Unicode completo (estremamente complesso, lungo decine di pagine), consultare l' Allegato n . 9 Unicode Standard .