diff --git a/t/example-nondet-parsing.t b/t/example-nondet-parsing.t new file mode 100644 index 00000000..4eb48dc1 --- /dev/null +++ b/t/example-nondet-parsing.t @@ -0,0 +1,19 @@ +#!perl -T +use 5.006; + +use strict; +use warnings; + +use Test::More; +use Language::Bel::Test; + +plan tests => 3; + +my $output = output_of_eval_file("t/nondet-parsing.bel"); + +my @lines = split(/\n/, $output); + +is scalar(@lines), 2, "anticipated number of lines of output"; +is $lines[0], "(seq \\a seq \\a \\a) ", "first line"; +is $lines[1], "(seq seq \\a \\a \\a) ", "second line"; + diff --git a/t/nondet-parsing.bel b/t/nondet-parsing.bel new file mode 100644 index 00000000..cca99db0 --- /dev/null +++ b/t/nondet-parsing.bel @@ -0,0 +1,39 @@ +;; Example based on https://users.monash.edu/~lloyd/tildeFP/1988BCJ/ + +;; (type parser (cont input trace) -> (listof trace)) +;; (type cont (input trace) -> (listof trace)) + +;; (ann fin cont) +(def fin (input trace) + (if (no input) + (list trace) + nil)) + +;; (ann letter (char) -> parser) +(def letter (ch) + (fn (cont input trace) + (if (no input) nil + (id ch (car input)) (cont (cdr input) (snoc trace ch)) + nil))) + +;; (ann seq (parser parser) -> parser) +(def seq (p1 p2) + (fn (cont input trace) + (p1 (fn (input2 trace2) + (p2 cont input2 trace2)) + input + (snoc trace 'seq)))) + +;; (ann either (parser parser) -> parser) +(def either (p1 p2) + (fn (cont input trace) + (append (p1 cont input trace) + (p2 cont input trace)))) + +(set a (letter \a) + aORaa (either a (seq a a)) + S (seq aORaa aORaa)) + +(each match (S fin "aaa" nil) + (prn match)) +