1use crate::err::*;
2use crate::iter::*;
3use crate::ptrait::*;
4use std::fmt::Debug;
5
6#[derive(Clone)]
7pub struct Maybe<A: Parser> {
8 p: A,
9}
10
11impl<A> Parser for Maybe<A>
12where
13 A: Parser,
14{
15 type Out = Option<A::Out>;
16 fn parse<'a>(&self, i: &LCChars<'a>) -> ParseRes<'a, Self::Out> {
17 match self.p.parse(i) {
18 Ok((ir, v, ex)) => Ok((ir, Some(v), ex)),
19 Err(e) => Ok((i.clone(), None, Some(e))),
20 }
21 }
22}
23
24pub fn maybe<P: Parser>(p: P) -> Maybe<P> {
43 Maybe { p }
44}
45
46pub struct Exists<P: Parser> {
47 p: P,
48}
49
50impl<P: Parser> Parser for Exists<P> {
51 type Out = bool;
52 fn parse<'a>(&self, it: &LCChars<'a>) -> ParseRes<'a, bool> {
53 match self.p.parse(it) {
54 Ok((nit, _, e)) => Ok((nit, true, e)),
55 Err(e) => Ok((it.clone(), false, Some(e))),
56 }
57 }
58}
59
60pub fn exists<P: Parser>(p: P) -> Exists<P> {
61 Exists { p }
62}
63
64#[derive(Clone)]
65pub struct Wrap<A, B> {
66 a: A,
67 b: B,
68}
69
70impl<A, B> Parser for Wrap<A, B>
71where
72 A: Parser,
73 B: Parser,
74{
75 type Out = B::Out;
76 fn parse<'a>(&self, i: &LCChars<'a>) -> ParseRes<'a, Self::Out> {
77 let (i, _, c1) = self.a.parse(i)?;
78 let (i, res, c2) = self.b.parse(&i).map_err(|e| e.join_op(c1))?;
79 let (n, _, c3) = self.a.parse(&i).map_err(|e| e.join_op(c2))?;
80 Ok((n, res, c3))
81 }
82}
83
84pub fn wrap<A, B>(a: A, b: B) -> Wrap<A, B>
85where
86 A: Parser,
87 B: Parser,
88{
89 Wrap { a, b }
90}
91
92impl<P: Parser<Out = V>, V: Debug> Parser for FailOn<P> {
93 type Out = ();
94 fn parse<'a>(&self, it: &LCChars<'a>) -> ParseRes<'a, ()> {
95 match self.p.parse(it) {
96 Ok((_, _, _)) => it.err_rp(self),
97 Err(_) => Ok((it.clone(), (), None)),
98 }
99 }
100 fn expected(&self) -> Expected {
101 Expected::except(self.p.expected())
102 }
103}
104
105pub struct FailOn<P: Parser> {
106 p: P,
107}
108
109pub fn fail_on<P: Parser>(p: P) -> FailOn<P> {
110 FailOn { p }
111}
112
113#[derive(PartialEq, Debug, Clone)]
114pub struct PDebugger<P: Parser> {
115 p: P,
116 s: &'static str,
117}
118
119pub fn debug<P: Parser>(p: P, s: &'static str) -> PDebugger<P> {
120 PDebugger { p, s }
121}
122
123impl<P: Parser> Parser for PDebugger<P> {
124 type Out = P::Out;
125 fn parse<'a>(&self, it: &LCChars<'a>) -> ParseRes<'a, Self::Out> {
126 println!("DebuggerPre - {}", self.s);
127 let r = self.p.parse(it);
128 match &r {
129 Ok((nit, _, _)) => {
130 let s = match (it.index(), nit.index()) {
131 (Some(st), Some(f)) => &it.as_str()[..f - st],
132 _ => it.as_str(),
133 };
134 println!("Success - {}, \"{}\"", self.s, s);
135 }
136 Err(_) => println!("Fail - {}", self.s),
137 };
138 r
139 }
140}