mirror of
https://github.com/MorizzG/MLox.git
synced 2025-12-06 04:22:41 +00:00
implemented function calls
This commit is contained in:
parent
0dc19b4fdf
commit
b717b91ee5
3 changed files with 94 additions and 21 deletions
|
|
@ -87,17 +87,37 @@ let rec interpret_expr (env : environment) (expr_node : expr_node) :
|
|||
in
|
||||
let* args = List.fold_left f (Ok []) args in
|
||||
let args = List.rev args in
|
||||
(* let args_s =
|
||||
List.fold_left (fun acc value -> acc ^ " " ^ string_of_lox_value value) "" args
|
||||
in
|
||||
Printf.eprintf "Called %s with args%s\n%!" (string_of_lox_value callee) args_s; *)
|
||||
match callee with
|
||||
| Function (NativeFunction { name; arity; fn }) ->
|
||||
let args_len = List.length args in
|
||||
if args_len <> arity then
|
||||
let msg =
|
||||
Printf.sprintf "Native Function %s has arity %d, but was called with %d args" name
|
||||
args_len arity
|
||||
in
|
||||
RuntimeError.make pos msg |> Result.error
|
||||
else fn args |> Result.map_error (RuntimeError.make pos)
|
||||
| Function (LoxFunction { name; arity; arg_names; body }) ->
|
||||
let args_len = List.length args in
|
||||
if args_len <> arity then
|
||||
let msg =
|
||||
Printf.sprintf "Function %s has arity %d, but was called with %d args" name args_len
|
||||
arity
|
||||
in
|
||||
RuntimeError.make pos msg |> Result.error
|
||||
else
|
||||
let env = Env.push_frame env in
|
||||
let () =
|
||||
List.iter2 (fun name value -> assert (Env.define env name value)) arg_names args
|
||||
in
|
||||
let* () = interpret_stmt env body in
|
||||
Ok Nil
|
||||
| _ ->
|
||||
ignore args;
|
||||
let msg = Printf.sprintf "%s object is not callable" (type_string_of_lox_value callee) in
|
||||
RuntimeError.make pos msg |> Result.error)
|
||||
|
||||
let rec interpret_stmt (env : environment) (stmt_node : stmt_node) : (unit, runtime_error) result =
|
||||
and interpret_stmt (env : environment) (stmt_node : stmt_node) : (unit, runtime_error) result =
|
||||
let { pos; stmt } = stmt_node in
|
||||
ignore pos;
|
||||
match stmt with
|
||||
|
|
@ -116,7 +136,19 @@ let rec interpret_stmt (env : environment) (stmt_node : stmt_node) : (unit, runt
|
|||
let success = Env.define env name init in
|
||||
if success then Ok ()
|
||||
else
|
||||
let msg = Printf.sprintf "Tried to define %s, but was already defined" name in
|
||||
let msg =
|
||||
Printf.sprintf "Tried to define %s, but a variable of that name was already defined" name
|
||||
in
|
||||
RuntimeError.make pos msg |> Result.error
|
||||
| FunDecl { name; arg_names; body } ->
|
||||
let fn = make_lox_function name arg_names body in
|
||||
let success = Env.define env name fn in
|
||||
if success then Ok ()
|
||||
else
|
||||
let msg =
|
||||
Printf.sprintf
|
||||
"Tried to define function %s, but a variable of that name was already defined" name
|
||||
in
|
||||
RuntimeError.make pos msg |> Result.error
|
||||
| Block stmts ->
|
||||
let env = Env.enter env in
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue