我有一个手写的预测解析器。每个非终结符都有一个对应的解析方法。每个解析器方法的类型都是 tokenlist -> tokenlist * Ast`
在每个方法中,我使用约定“tokenlist_symbol”在使用特定符号后暗示令牌列表。在这一行中:let typ tokenlist_typ = parseTyp tokenlist in match tokenlist.head with
typ 是一个 AST,而 tokenlist_typ 是 parseTyp 消耗了 typ 前缀后的令牌列表的剩余部分。
但是,我收到This expression has type 'a -> token_list * Ast.typ but an expression was expected of type Ast.typ
行错误,(Ast.Declaration(typ, identifier, decls_prime), tokenlist_decls_prime)
type token_list =
{head : Lexer.token; (** head token. *)
lexbuf : Lexer.token list} (** lexer buffer. *)
(** Represents a parser buffer used during parsing of various productions. *)
let default_tokenlist s = {head = Lexer.EOF; lexbuf = Lexer.tokenize s}
(* Create a default [parse_buffer] with the given string [s]. *)
let next tokenlist =
let {head = _; lexbuf = buf} = tokenlist in
{head = List.hd buf; lexbuf = List.tl buf}
(** Retrieves a new parser buffer with the next lookahead token. *)
let parseTyp tokenlist =
match tokenlist.head with
| Lexer.Int -> (next tokenlist, Ast.Int)
| Lexer.Bool -> (next tokenlist, Ast.Bool)
| Lexer.Void -> (next tokenlist, Ast.Void)
| Lexer.EOF -> (tokenlist, Ast.Epsilon)
| _-> let err_msg = "Syntax Error" in
raise (Syntax_error err_msg)
(*decls = typ “id” decls_prime | epsilon *)
let rec parseDecls tokenlist =
let (tokenlist_typ, typ, ) = parseTyp tokenlist in
match tokenlist.head with
| Lexer.ID identifier -> let (tokenlist_decls_prime, decls_prime) = next tokenlist |> parseDeclsPrime in
(tokenlist_decls_prime, Ast.Declaration(typ, identifier, decls_prime))
| Lexer.EOF -> (tokenlist, [])
| _-> let err_msg = Printf.sprintf "Syntax Error" in
raise (Syntax_error err_msg)
(* decls_prime = vdecl decls | fdecl decls *)
and parseDeclsPrime tokenlist =
match tokenlist.head with
| Lexer.Semicolon -> let tokenlist_vdecl) = next tokenlist in
let (tokenlist_decls, decls) = parseDecls tokenlist_vdecl in
(tokenlist_decls, Ast.DeclsPrime(Lexer.Semicolon, vdecl, decls))
| Lexer.LeftParens -> let (tokenlist_fdecl, fdecl) = next tokenlist |> parseFdecl in
let (tokenlist_decls, decls) = parseDecls tokenlist_fdecl in
(tokenlist_decls, Ast.DeclsPrime(Lexer.Semicolon, fdecl, decls))
| _-> let err_msg = Printf.sprintf "Syntax Error" in
raise (Syntax_error err_msg)
你有这个:
let (decls_prime, tokenlist_decls_prime) =
next tokenlist |> parseDeclsPrime
从名称来看,这看起来像是parseDeclsPrime
返回 type Ast * tokenlist
。但在我看来,解析函数应该返回tokenlist * Ast
。
这对中的两个名字很可能是颠倒的。
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句