Skip to main content

ct_regex_internal/matcher/
quantifier.rs

1use std::fmt::{self, Debug};
2use std::marker::PhantomData;
3use std::{iter, vec};
4
5use crate::expr::IndexedCaptures;
6use crate::haystack::{HaystackItem, HaystackOf};
7use crate::matcher::{LazyMatcher, Matcher, impl_all_captures_single, impl_all_matches_single};
8use crate::sealed::Sealed;
9
10#[derive(#[automatically_derived]
impl<I: ::core::default::Default + HaystackItem, A: ::core::default::Default +
    Matcher<I>, const N : usize> ::core::default::Default for
    QuantifierN<I, A, N> {
    #[inline]
    fn default() -> QuantifierN<I, A, N> {
        QuantifierN(::core::default::Default::default(),
            ::core::default::Default::default())
    }
}Default, #[automatically_derived]
impl<I: ::core::clone::Clone + HaystackItem, A: ::core::clone::Clone +
    Matcher<I>, const N : usize> ::core::clone::Clone for QuantifierN<I, A, N>
    {
    #[inline]
    fn clone(&self) -> QuantifierN<I, A, N> {
        QuantifierN(::core::clone::Clone::clone(&self.0),
            ::core::clone::Clone::clone(&self.1))
    }
}Clone, #[automatically_derived]
impl<I: ::core::marker::Copy + HaystackItem, A: ::core::marker::Copy +
    Matcher<I>, const N : usize> ::core::marker::Copy for QuantifierN<I, A, N>
    {
}Copy)]
11pub struct QuantifierN<I: HaystackItem, A: Matcher<I>, const N: usize>(
12    pub(crate) PhantomData<I>,
13    pub(crate) PhantomData<A>,
14);
15
16impl<I: HaystackItem, A: Matcher<I>, const N: usize> Sealed for QuantifierN<I, A, N> {}
17
18impl<I: HaystackItem, A: Matcher<I>, const N: usize> Matcher<I> for QuantifierN<I, A, N> {
19    fn matches<'a, H: HaystackOf<'a, I>>(hay: &mut H) -> bool {
20        let mut count = 0;
21        while A::matches(hay) {
22            count += 1;
23        }
24        count == N
25    }
26
27    I
crate::matcher::AllMatchesSingle
I
&mut H
hay
Self::AllMatches<'a, H>
crate::matcher::all_matches_single::<I, H, Self>(hay);impl_all_matches_single!(I);
28
29    fn captures<'a, H: HaystackOf<'a, I>>(hay: &mut H, caps: &mut IndexedCaptures) -> bool {
30        let mut count = 0;
31        while A::captures(hay, caps) {
32            count += 1;
33        }
34        count == N
35    }
36
37    I
crate::matcher::AllCapturesSingle
I
&mut H
hay
&mut IndexedCaptures
caps
Self::AllCaptures<'a, H>
crate::matcher::all_captures_single::<I, H, Self>(hay, caps);impl_all_captures_single!(I);
38}
39
40impl<I: HaystackItem, A: Matcher<I>, const N: usize> Debug for QuantifierN<I, A, N> {
41    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
42        f.write_fmt(format_args!("{0:?}{{{1}}}", A::default(), N))write!(f, "{:?}{{{N}}}", A::default())
43    }
44}
45
46pub type AllMatchesMultiple = iter::Rev<vec::IntoIter<usize>>;
47pub type AllCapturesMultiple = iter::Rev<vec::IntoIter<(usize, IndexedCaptures)>>;
48
49#[derive(#[automatically_derived]
impl<I: ::core::default::Default + HaystackItem, A: ::core::default::Default +
    Matcher<I>, const N : usize> ::core::default::Default for
    QuantifierNOrMore<I, A, N> {
    #[inline]
    fn default() -> QuantifierNOrMore<I, A, N> {
        QuantifierNOrMore(::core::default::Default::default(),
            ::core::default::Default::default())
    }
}Default, #[automatically_derived]
impl<I: ::core::clone::Clone + HaystackItem, A: ::core::clone::Clone +
    Matcher<I>, const N : usize> ::core::clone::Clone for
    QuantifierNOrMore<I, A, N> {
    #[inline]
    fn clone(&self) -> QuantifierNOrMore<I, A, N> {
        QuantifierNOrMore(::core::clone::Clone::clone(&self.0),
            ::core::clone::Clone::clone(&self.1))
    }
}Clone, #[automatically_derived]
impl<I: ::core::marker::Copy + HaystackItem, A: ::core::marker::Copy +
    Matcher<I>, const N : usize> ::core::marker::Copy for
    QuantifierNOrMore<I, A, N> {
}Copy)]
50pub struct QuantifierNOrMore<I: HaystackItem, A: Matcher<I>, const N: usize>(
51    pub(crate) PhantomData<I>,
52    pub(crate) PhantomData<A>,
53);
54
55impl<I: HaystackItem, A: Matcher<I>, const N: usize> Sealed for QuantifierNOrMore<I, A, N> {}
56
57impl<I: HaystackItem, A: Matcher<I>, const N: usize> Matcher<I> for QuantifierNOrMore<I, A, N> {
58    type AllMatches<'a, H: HaystackOf<'a, I>> = AllMatchesMultiple;
59    type AllCaptures<'a, H: HaystackOf<'a, I>> = AllCapturesMultiple;
60
61    fn matches<'a, H: HaystackOf<'a, I>>(hay: &mut H) -> bool {
62        let mut count = 0;
63        while A::matches(hay) {
64            count += 1;
65        }
66        count >= N
67    }
68
69    // This **has to be** evaluated eagerly, so we use a vec.
70    fn all_matches<'a, H: HaystackOf<'a, I>>(hay: &mut H) -> Self::AllMatches<'a, H> {
71        Self::lazy_all_matches(hay)
72            .collect::<Vec<_>>()
73            .into_iter()
74            .rev()
75    }
76
77    fn captures<'a, H: HaystackOf<'a, I>>(hay: &mut H, caps: &mut IndexedCaptures) -> bool {
78        let mut count = 0;
79        while A::captures(hay, caps) {
80            count += 1;
81        }
82        count >= N
83    }
84
85    fn all_captures<'a, H: HaystackOf<'a, I>>(
86        hay: &mut H,
87        caps: &mut IndexedCaptures,
88    ) -> Self::AllCaptures<'a, H> {
89        Self::lazy_all_captures(hay, caps)
90            .collect::<Vec<_>>()
91            .into_iter()
92            .rev()
93    }
94}
95
96impl<I: HaystackItem, A: Matcher<I>, const N: usize> Debug for QuantifierNOrMore<I, A, N> {
97    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
98        f.write_fmt(format_args!("{0:?}{{{1},}}", A::default(), N))write!(f, "{:?}{{{N},}}", A::default())
99    }
100}
101
102#[derive(#[automatically_derived]
impl<I: ::core::default::Default + HaystackItem, A: ::core::default::Default +
    Matcher<I>, const N : usize, const M : usize> ::core::default::Default for
    QuantifierNToM<I, A, N, M> {
    #[inline]
    fn default() -> QuantifierNToM<I, A, N, M> {
        QuantifierNToM(::core::default::Default::default(),
            ::core::default::Default::default())
    }
}Default, #[automatically_derived]
impl<I: ::core::clone::Clone + HaystackItem, A: ::core::clone::Clone +
    Matcher<I>, const N : usize, const M : usize> ::core::clone::Clone for
    QuantifierNToM<I, A, N, M> {
    #[inline]
    fn clone(&self) -> QuantifierNToM<I, A, N, M> {
        QuantifierNToM(::core::clone::Clone::clone(&self.0),
            ::core::clone::Clone::clone(&self.1))
    }
}Clone, #[automatically_derived]
impl<I: ::core::marker::Copy + HaystackItem, A: ::core::marker::Copy +
    Matcher<I>, const N : usize, const M : usize> ::core::marker::Copy for
    QuantifierNToM<I, A, N, M> {
}Copy)]
103pub struct QuantifierNToM<I: HaystackItem, A: Matcher<I>, const N: usize, const M: usize>(
104    pub(crate) PhantomData<I>,
105    pub(crate) PhantomData<A>,
106);
107
108impl<I: HaystackItem, A: Matcher<I>, const N: usize, const M: usize> Sealed for QuantifierNToM<I, A, N, M> {}
109
110impl<I: HaystackItem, A: Matcher<I>, const N: usize, const M: usize> Matcher<I> for QuantifierNToM<I, A, N, M> {
111    type AllMatches<'a, H: HaystackOf<'a, I>> = AllMatchesMultiple;
112    type AllCaptures<'a, H: HaystackOf<'a, I>> = AllCapturesMultiple;
113
114    fn matches<'a, H: HaystackOf<'a, I>>(hay: &mut H) -> bool {
115        let mut count = 0;
116        loop {
117            if count >= N && count == M {
118                return true;
119            }
120            if A::matches(hay) {
121                count += 1;
122            } else {
123                break;
124            }
125        }
126        N <= count && count <= M
127    }
128
129    fn all_matches<'a, H: HaystackOf<'a, I>>(hay: &mut H) -> Self::AllMatches<'a, H> {
130        Self::lazy_all_matches(hay)
131            .collect::<Vec<_>>()
132            .into_iter()
133            .rev()
134    }
135
136    fn captures<'a, H: HaystackOf<'a, I>>(hay: &mut H, caps: &mut IndexedCaptures) -> bool {
137        let mut count = 0;
138        loop {
139            if count >= N && count == M {
140                return true;
141            }
142            if A::captures(hay, caps) {
143                count += 1;
144            } else {
145                break;
146            }
147        }
148        N <= count && count <= M
149    }
150
151    fn all_captures<'a, H: HaystackOf<'a, I>>(
152        hay: &mut H,
153        caps: &mut IndexedCaptures,
154    ) -> Self::AllCaptures<'a, H> {
155        Self::lazy_all_captures(hay, caps)
156            .collect::<Vec<_>>()
157            .into_iter()
158            .rev()
159    }
160}
161
162impl<I: HaystackItem, A: Matcher<I>, const N: usize, const M: usize> Debug for QuantifierNToM<I, A, N, M> {
163    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
164        f.write_fmt(format_args!("{0:?}{{{1},{2}}}", A::default(), N, M))write!(f, "{:?}{{{N},{M}}}", A::default())
165    }
166}