Come esercizio, scrivo da zero un parser per Haskell. Nel realizzare il lexer, ho notato le seguenti regole sul Rapporto Haskell 2010 :
cifra → ascDigit | uniDigit
ascDigit →0
|1
| ... |9
uniDigit → qualsiasi Unicode decimale cifre
octit →0
|1
| ... |7
esadecimale → cifra |A
| ... |F
|a
| ... |f
decimale → cifra { cifra }
ottale → ottit { octit }
esadecimale → hexit { hexit }intero → decimale |
0o
ottale |0O
ottale |0x
esadecimale | float0X
esadecimale → decimale decimale [ esponente ] | decimale esponente esponente → ( | ) [ | ] decimale
.
e
E
+
-
I letterali decimali ed esadecimali, insieme ai letterali float, sono tutti basati su digit , che ammette qualsiasi cifra decimale Unicode, anziché ascDigit , che ammette solo le cifre di base 0-9 da ASCII. Stranamente, l' ottale si basa su ottit , che invece ammette solo le cifre ASCII 0-7. Immagino che queste "cifre decimali Unicode" siano punti di codice Unicode con la categoria generale "Nd". Tuttavia, questo include caratteri come le cifre a larghezza intera 0-9 e i numeri Devanagari ०-९. Posso capire perché potrebbe essere desiderabile consentirli negli identificatori, ma non vedo alcun beneficio nel consentire a uno di scrivere ९0
per il letterale 90
.
GHC sembra essere d'accordo con me. Quando provo a compilare questo file,
module DigitTest where
x1 = 1
sputa questo errore.
digitTest1.hs:2:6: error: lexical error at character '\65297'
|
2 | x1 = 1
| ^
Tuttavia, questo file
module DigitTest where
x1 = 1
compila bene. Sto leggendo le specifiche della lingua in modo errato? Il comportamento (sensibile) di GHC è effettivamente corretto o è tecnicamente contrario alle specifiche del Rapporto? Non riesco a trovare alcuna menzione di questo da nessuna parte.