let descan = function
| COLON -> ":"
| NEWLINE -> "\n"
| SPACE(n) -> String.make n ' '
| REFINABLE -> "refinable"
| AND -> "and"
| OR -> "or"
| XOR -> "xor"
| NAND -> "nand"
| NOR -> "nor"
| NOT -> "not"
| EQ -> "="
| NEQ -> "=/="
| LT -> "<"
| LEQ -> "<="
| GT -> ">"
| GEQ -> ">="
| ARRAY -> "[]"
| LBRACKET -> "["
| RBRACKET -> "]"
| LPAREN -> "("
| RPAREN -> ")"
| LBRACE -> "{"
| RBRACE -> "}"
| SEMI -> ";"
| COMMA -> ","
| PLUS -> "+"
| MINUS -> "-"
| TIMES -> "*"
| DIVIDE -> "/"
| MOD -> "%"
| POWER -> "^"
| PLUSA -> "+="
| MINUSA -> "-="
| TIMESA -> "*="
| DIVIDEA -> "/="
| MODA -> "%="
| POWERA -> "^="
| IF -> "if"
| ELSE -> "else"
| ELSIF -> "elsif"
| WHILE -> "while"
| RETURN -> "return"
| CLASS -> "class"
| EXTEND -> "extends"
| SUPER -> "super"
| INIT -> "init"
| NULL -> "null"
| VOID -> "void"
| THIS -> "this"
| REFINE -> "refine"
| REFINES -> "refinement"
| TO -> "to"
| PRIVATE -> "private"
| PUBLIC -> "public"
| PROTECTED -> "protected"
| DOT -> "."
| MAIN -> "main"
| NEW -> "new"
| ASSIGN -> ":="
| ID(var) -> var
| TYPE(typ) -> typ
| BLIT(b) -> if b then "true" else "false"
| ILIT(i) -> string_of_int(i)
| FLIT(f) -> string_of_float(f)
| SLIT(s) -> Format.sprintf "\"%s\"" s
| EOF -> "eof"