ocaml: phase 2 function | pat -> body (+4 tests, 198 total)
Some checks failed
Test, Build, and Deploy / test-build-deploy (push) Failing after 54s

Sugar for fun + match. AST (:function CLAUSES) -> unary closure that
runs ocaml-match-clauses on its arg. let rec recognises :function as a
recursive rhs and ties the knot via cell, so

  let rec map f = function | [] -> [] | h::t -> f h :: map f t

works. ocaml-match-eval refactored to share clause-walk with function.
This commit is contained in:
2026-05-08 08:15:38 +00:00
parent 9b8b0b4325
commit 937342bbf0
4 changed files with 114 additions and 54 deletions

View File

@@ -148,8 +148,7 @@ SX CEK evaluator (both JS and OCaml hosts)
- [~] `let`/`let rec`/`let ... in` (single-binding done; mutually recursive
`and` deferred).
- [x] Lambda + application (curried by default — auto-curry multi-param defs).
- [ ] `fun`/`function` (single-arg lambda with immediate match on arg). _(`fun`
done; `function` blocked on parser support.)_
- [x] `fun`/`function` (single-arg lambda with immediate match on arg).
- [x] `if`/`then`/`else`, `begin`/`end`, sequence `;`.
- [x] Arithmetic, comparison, boolean ops, string `^`, `mod`.
- [x] Unit `()` value; `ignore`.
@@ -321,6 +320,13 @@ the "mother tongue" closure: OCaml → SX → OCaml. This means:
_Newest first._
- 2026-05-08 Phase 2 — `function | pat -> body | …` parser + eval.
Sugar for `fun x -> match x with | …`. AST: `(:function CLAUSES)`
evaluated to a unary closure that runs `ocaml-match-clauses` on the
argument. `let rec` knot also triggers when rhs is `:function`, so
`let rec map f = function | [] -> [] | h::t -> f h :: map f t` works.
ocaml-match-eval refactored to share `ocaml-match-clauses` with the
function form. 198/198 (+4).
- 2026-05-08 Phase 2 — `for`/`while` loops. `(:for NAME LO HI DIR BODY)`
with `:ascend`/`:descend` direction (`to`/`downto`); `(:while COND BODY)`.
Both eval to unit and re-bind the loop var per iteration. 194/194 (+5).