Hello. I’m trying to write a parser for a simple language with AST definition as follows
type term =
| TmTrue
| TmFalse
| TmIf of term * term * term
| TmZero
I’m struggling to write the parser for if expressions. An example if expression is like
if false then true else false;
What I’ve got so far
open Angstrom
let ws =
skip_while (function '\x20' | '\x0a' | '\x0d' | '\x09' -> true | _ -> false)
let lchar c = ws *> char c
let lrchar c = ws *> char c <* ws
let lrstring s = ws *> string s <* ws
let _true = lrstring "true" *> return TmTrue
let _false = lrstring "false" *> return TmFalse
let zero = lrchar '0' *> return TmZero
let expr =
fix (fun expr ->
let ifelse =
lrstring "if" *> expr >>= fun cond ->
lrstring "then" *> expr >>= fun thenexpr ->
lrstring "else" *> expr >>| fun elseexpr ->
return (TmIf (cond, thenexpr, elseexpr))
in
choice [ _true; _false; zero; ifelse ])
However, this gives me a type error saying that the ifelse
function has type term t t
, but expected term t
. I don’t get how the parser I’ve wrote has that type, if anyone could explain, I’d be really glad.
I also tried to use recursive function, however it gave “this kind of expression is not allowed in let rec
”:
let rec ifelse =
lrstring "if" *> expr >>= fun cond ->
lrstring "then" *> expr >>= fun then_exp ->
lrstring "else" *> expr >>= fun else_exp ->
return (TmIf (cond, then_exp, else_exp))
and expr = choice [ _true; _false; zero; ifelse ]
Thanks!