Commits

Sebastien Mondet committed b6fb475

doc: add more details to the example

  • Participants
  • Parent commits 3f2a5cd

Comments (0)

Files changed (1)

 Example
 -------
 
+### Demo
+
 Let's say we define an AST for a basic language:
 
 ```ocaml
 let parser =
   let open Meta_parser in
   let rec expr_gram =
-    lazy (Lazy.force (
+    lazy (Lazy.force (  (* necessary hack to write recursive values *)
         try_in_order ~name:"DSL Expression" [
           apply integer ~f:(fun i ~loc -> `Ok (Int i));
           apply float   ~f:(fun s ~loc -> `Ok (Float s));
            "[DSL Expression]: try [{int}] then [{float}] then \
            [{{parse [Kwd +] and continue with [sequence [...]]}}]")))
 ```
+
+### Details
+
+Let's see some details about the previous example:
+
+````ocaml
+let parser =
+  let open Meta_parser in
+  let rec expr_gram =
+    lazy (Lazy.force (
+  ...
+````
+
+the value describing the grammar in the EDSL is recursive since the grammar is
+receursive, it uses `let rec` and hence needs a `lazy (Lazy.force ...)` hack to
+be accepted.
+
+Then we use the functions of the `Meta_parser` module to build the “program”:
+
+```ocaml
+# Meta_parser.try_in_order;;
+- : ?name:string ->
+    ('a, 'b) Sexp_parser_edsl.Meta_parser.t list ->
+    ('a, 'b) Sexp_parser_edsl.Meta_parser.t
+    = <fun>
+```
+
+The function `try_in_order` takes a list of grammars and tries them
+sequentially until one succeeds.
+
+``` ocaml
+# Meta_parser.apply;;
+- : ('a, 'error) Sexp_parser_edsl.Meta_parser.t ->
+    f:('a ->
+       loc:Sexp_parser_edsl.Meta_parser.location ->
+       ('c, 'error) Sexp_parser_edsl.result) ->
+    ('c, 'error) Sexp_parser_edsl.Meta_parser.t
+= <fun>
+```
+
+To convert a the result of the parsing of a given grammar one must `apply` a
+function to it.
+
+```ocaml
+# let natural x ~loc = if x >= 0 then `Ok x else `Error (`not_positive (loc, x));;
+val natural :
+  int -> loc:'a -> [> `Error of [> `not_positive of 'a * int ] | `Ok of int ] =
+  <fun>
+# let natural_parser = Meta_parser.( apply integer ~f:natural);;
+val natural_parser :
+  (int, _[> `not_positive of Sexp_parser_edsl.Meta_parser.location * int ])
+  Sexp_parser_edsl.Meta_parser.t = <lazy>
+```
+
+hence `natural_parser` is a parser which tries to parse positive integers and
+*adds* `not_positive` to the set of possible errors.
+