【发布时间】:2015-05-03 02:35:19
【问题描述】:
我目前正在为 ocaml 中的 c flat 编写解释器。我得到了一个包含抽象语法树文件、主文件等的源代码生成文件。我正在尝试实现算术,但在运行测试用例时我不断收到此错误(match_failure)。测试用例位于 .cf 文件中。这是文件的内容 “print_int((9+6+(11/11)+1+(-6))*(-1));” 有人可以帮我理解为什么会发生错误吗?
这是我的代码:
open Ast;;
open Env;;
open Store;;
let allocateMem env = env;; (* TODO: implement this function *)
let rec eval_expr (expr:expr) (ps:proc_state) (env:environment) (store:store) : int = match expr with
Add (e1, e2) ->
let r1 = eval_expr e1 ps env store in
let r2 = eval_expr e2 ps env store in
r1 + r2
| Sub (e1, e2) ->
let r1 = eval_expr e1 ps env store in
let r2 = eval_expr e2 ps env store in
r1 - r2
| Mul (e1, e2) ->
let r1 = eval_expr e1 ps env store in
let r2 = eval_expr e2 ps env store in
r1 * r2
| Div (e1, e2) ->
let r1 = eval_expr e1 ps env store in
let r2 = eval_expr e2 ps env store in
r1 / r2
| Neg (e1) ->
let r1 = eval_expr e1 ps env store in
r1 * -1
| IntConst i -> i
| Id (e1) ->
let l = binding_of env e1 in
let Intval(i)= value_at(store,l) in
i;;
;;
(* eval_expr: expr -> proc_state -> env -> store -> value *)
let rec eval_cond cond ps env store = match cond with
Equal (e1, e2) ->
let r1 = eval_expr e1 ps env store in
let r2 = eval_expr e2 ps env store in
r1 == r2
(* TODO: add more *)
;;
type stmtEvalRes = Next | BreakOut | ContinueOn;;
(* eval_stmt: stmt -> proc_state -> env -> store -> stmtEvalRes*proc_state *)
let rec eval_stmt stmt ps env store = match stmt with
| PrintInt e ->
let r = eval_expr e ps env store in
print_int r; (Next, ps, store)
| PrintStr s ->
print_string (Str.global_replace (Str.regexp "\\\\n") "\n" s);
(* Escaping characters here because it's not done in the parser *)
(Next, ps, store)
| List (stmt1::stmts) -> eval_stmt stmt1 ps env store
(* TODO: complete this case so that all statements in the list evaluated *)
;;
【问题讨论】:
-
请发布足够的代码来重现错误。还请发布您在编译代码时收到的任何编译器警告。
-
我更新了。另外,我没有收到任何警告。
-
如果您遇到匹配失败,我不明白这怎么可能是真的 - 除非您明确禁用详尽警告。请注意,如果您在不更改代码或运行
make clean的情况下运行 make 将不会收到任何警告,因为它不会编译任何未更改的文件。 -
无论如何,当我说“重现错误”时,我的意思是“编译你的代码,运行它并得到与你相同的错误”。当我尝试运行您的代码时,我收到一堆关于未定义类型和构造函数的编译错误。很明显,这不足以重现错误。如果您可以将问题减少到包含所有相关定义的单个文件,可以编译和运行并在运行时产生相同的错误消息(同时希望通过删除与错误而不破坏程序)。
-
我做了 make clean 然后 make all ,我得到了这个警告:“警告 8:这个模式匹配并不详尽。这是一个不匹配的值的例子:(Sub (, _)|Mul (, )|Div (, )|Neg _|Id _|At (, )|Deref _ |AddressOf _| 调用 (, _)|Pre _|Post _) "
标签: pattern-matching ocaml match