Parser traits in submodule

This commit is contained in:
Greg Shuflin 2024-01-27 16:16:54 -08:00
parent afae0d0840
commit 918e3d042b
2 changed files with 47 additions and 44 deletions

View File

@ -2,59 +2,17 @@
mod choice; mod choice;
mod combinators; mod combinators;
mod map; mod map;
mod parser;
mod primitives; mod primitives;
mod sequence; mod sequence;
pub use choice::*; pub use choice::*;
pub use combinators::*; pub use combinators::*;
pub use map::*; pub use map::*;
pub use parser::{ParseResult, Parser, ParserExtension};
pub use primitives::*; pub use primitives::*;
pub use sequence::*; pub use sequence::*;
type ParseResult<I, O, E> = Result<(O, I), (E, I)>;
pub trait Parser<I, O, E> {
fn parse(&self, input: I) -> ParseResult<I, O, E>;
}
impl<I, O, E, F> Parser<I, O, E> for F
where
F: Fn(I) -> ParseResult<I, O, E>,
{
fn parse(&self, input: I) -> ParseResult<I, O, E> {
self(input)
}
}
pub trait ParserExtension<I, O, E>: Parser<I, O, E> {
fn map<F, O2>(self, map_fn: F) -> impl Parser<I, O2, E>
where
F: Fn(O) -> O2;
fn to<O2: Clone>(self, item: O2) -> impl Parser<I, O2, E>;
fn then<O2, P: Parser<I, O2, E>>(self, next: P) -> impl Parser<I, (O, O2), E>;
}
impl<T, I, O, E> ParserExtension<I, O, E> for T
where
T: Parser<I, O, E>,
{
fn map<F, O2>(self, map_fn: F) -> impl Parser<I, O2, E>
where
F: Fn(O) -> O2,
{
map(self, map_fn)
}
fn to<O2: Clone>(self, item: O2) -> impl Parser<I, O2, E> {
self.map(move |_| item.clone())
}
fn then<O2, P: Parser<I, O2, E>>(self, next: P) -> impl Parser<I, (O, O2), E> {
seq2(self, next)
}
}
#[cfg(test)] #[cfg(test)]
mod tests { mod tests {
use super::*; use super::*;

45
src/parser.rs Normal file
View File

@ -0,0 +1,45 @@
use crate::{map, seq2};
pub type ParseResult<I, O, E> = Result<(O, I), (E, I)>;
pub trait Parser<I, O, E> {
fn parse(&self, input: I) -> ParseResult<I, O, E>;
}
impl<I, O, E, F> Parser<I, O, E> for F
where
F: Fn(I) -> ParseResult<I, O, E>,
{
fn parse(&self, input: I) -> ParseResult<I, O, E> {
self(input)
}
}
pub trait ParserExtension<I, O, E>: Parser<I, O, E> {
fn map<F, O2>(self, map_fn: F) -> impl Parser<I, O2, E>
where
F: Fn(O) -> O2;
fn to<O2: Clone>(self, item: O2) -> impl Parser<I, O2, E>;
fn then<O2, P: Parser<I, O2, E>>(self, next: P) -> impl Parser<I, (O, O2), E>;
}
impl<T, I, O, E> ParserExtension<I, O, E> for T
where
T: Parser<I, O, E>,
{
fn map<F, O2>(self, map_fn: F) -> impl Parser<I, O2, E>
where
F: Fn(O) -> O2,
{
map(self, map_fn)
}
fn to<O2: Clone>(self, item: O2) -> impl Parser<I, O2, E> {
self.map(move |_| item.clone())
}
fn then<O2, P: Parser<I, O2, E>>(self, next: P) -> impl Parser<I, (O, O2), E> {
seq2(self, next)
}
}