1use iregex::automata::{any_char, AnyRange, RangeSet};
2
3use crate::{Ast, Atom, Charset, Class, Classes, Disjunction, Repeat, Sequence};
4
5impl Ast {
6 pub fn build(&self) -> iregex::IRegEx {
7 let root = self.disjunction.build();
8
9 iregex::IRegEx {
10 root,
11 prefix: if self.start_anchor {
12 iregex::Affix::Anchor
13 } else {
14 iregex::Affix::Any
15 },
16 suffix: if self.end_anchor {
17 iregex::Affix::Anchor
18 } else {
19 iregex::Affix::Any
20 },
21 }
22 }
23}
24
25impl Disjunction {
26 pub fn build(&self) -> iregex::Alternation {
27 self.iter().map(Sequence::build).collect()
28 }
29}
30
31impl Sequence {
32 pub fn build(&self) -> iregex::Concatenation {
33 self.iter().map(Atom::build).collect()
34 }
35}
36
37impl Atom {
38 pub fn build(&self) -> iregex::Atom {
39 match self {
40 Self::Any => iregex::Atom::Token(any_char()),
41 Self::Char(c) => iregex::Atom::Token(RangeSet::from_iter([*c])),
42 Self::Set(set) => iregex::Atom::Token(set.build()),
43 Self::Group(g) => iregex::Atom::alternation(g.build()),
44 Self::Repeat(atom, repeat) => iregex::Atom::Repeat(atom.build().into(), repeat.build()),
45 }
46 }
47}
48
49impl Classes {
50 pub fn build(&self) -> iregex::automata::RangeSet<char> {
51 let mut result = iregex::automata::RangeSet::new();
52
53 for c in self {
54 result.extend(c.build());
55 }
56
57 result
58 }
59}
60
61impl Class {
62 pub fn build(&self) -> iregex::automata::RangeSet<char> {
63 todo!()
64 }
65}
66
67impl Charset {
68 pub fn build(&self) -> iregex::automata::RangeSet<char> {
69 let mut result = self.set.clone();
70 result.extend(self.classes.build());
71
72 if self.negative {
73 return result.gaps().map(AnyRange::cloned).collect();
74 } else {
75 result
76 }
77 }
78}
79
80impl Repeat {
81 pub fn build(&self) -> iregex::Repeat {
82 iregex::Repeat {
83 min: self.min,
84 max: self.max,
85 }
86 }
87}