From 99ea2dd415cdda1fe66adcddfbcee90a230403d0 Mon Sep 17 00:00:00 2001 From: Matthew Hall Date: Sat, 11 Mar 2023 15:59:27 +1300 Subject: Documentation for Parser --- src/parcom/parser.cr | 45 +++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 41 insertions(+), 4 deletions(-) diff --git a/src/parcom/parser.cr b/src/parcom/parser.cr index d74cbf8..ca350df 100644 --- a/src/parcom/parser.cr +++ b/src/parcom/parser.cr @@ -1,47 +1,84 @@ require "../parcom.cr" module Parcom + # `Parser` is the base class of all parser objects and contains + # a handful of helper methods that can allow for cleaner syntax. + # + # The generic type `T` represents the type of tokens a parser will + # operate on (usually `Char`). + # The generic type `V` represents the type of value that a parser + # will return when parsing is successful. abstract class Parser(T, V) + # Accepts a `Tokens(T)` and either retuns a `Result(T, V)`, or raises a + # `ParserFail` exception with a message providing context of where + # in the chain the parsing failed. + # + # The `V` in the returned `Result` is arbitrary, but the `Tokens(T)` in + # the returned result MUST contain the parser's input, with some tokens + # removed from the front proprtional to what was parsed. + # + # Example: + # ``` + # hello = ParsesHello.new # inherits from Parser(Char, String) + # input = Tokens.from_string("Hello world!") + # + # result = hello.parse(input) + # result.value # => "Hello" + # result.tokens # => [' ', 'w', 'o', 'r', 'l', 'd', '!'] + # + # bad_input = Tokens.from_string("Good evening world!") + # hello.parse(bad_input) # raises ParserFail + # ``` abstract def parse(tokens : Tokens(T)) : Result(T, V) + # Same as `#parse`, but returns `nil` instead of raising `ParserFail`. def parse?(tokens : Tokens(T)) : Result(T, V)? self.parse(tokens) rescue ParserFail return nil end + # Constructs an `Alt` parser with `self` and `other`. def |(other : Parser(T, V)) : Alt(T, V) Alt.new(self, other) end + # Constructs a `Plus` parser with `self` and `other`. def +(other : Parser(T, U)) : Plus(T, V, U) forall U Plus.new(self, other) end + # Constructs a `Left` parser with `self` and `other`. def <<(other : Parser(T, U)) : Left(T, V, U) forall U Left.new(self, other) end + # Constructs a `Right` parser with `self` and `other`. def >>(other : Parser(T, U)) : Right(T, V, U) forall U Right.new(self, other) end - def assert(f : V -> Bool) - Assert.new(self, &f) + # Constructs an `Assert` parser with `self` and the given block. + def assert(&block : V -> Bool) : Assert(T, V) + Assert.new(self, &block) end - def assert(&block : V -> Bool) - Assert.new(self, &block) + # Constructs an `Assert` parser with `self` and the given proc. + def assert(f : V -> Bool) : Assert(T, V) + Assert.new(self, &f) end + # Constructs a `Map` parser with `self` and the given block. def map(&block : V -> U) : Map(T, V, U) forall U Map.new(self, &block) end + # Constructs a `Map` parser with `self` and the given proc. def map(f : V -> U) : Map(T, V, U) forall U Map.new(self, &f) end + # Constructs a `Recover` parser with `self` and the given `V`. def recover(default : V) : Recover(T, V) Recover.new(self, default) end -- cgit v1.2.1