Skip to main content

shrimple_parser/pattern/
into_pattern.rs

1use super::Pattern;
2
3/// A trait for converting values into patterns. It exists to bridge the gap between an easy to use
4/// library & a more performant, lean implementation.
5///
6/// All parsers that accept patterns for matching should accept `IntoPattern` values for better
7/// ergonomics
8pub trait IntoPattern {
9    /// The pattern that this value converts to.
10    type Pattern: Pattern;
11
12    /// Converts the value into a pattern.
13    fn into_pattern(self) -> Self::Pattern;
14}
15
16impl<T: Pattern> IntoPattern for T {
17    type Pattern = Self;
18
19    fn into_pattern(self) -> Self::Pattern {
20        self
21    }
22}
23
24macro_rules! tuple_into_cons_list {
25    ($first:ident, $($next:ident),*) => { ($first, tuple_into_cons_list!($($next),+)) };
26    ($only:ident) => { $only }
27}
28
29macro_rules! impl_into_pattern_for_tuple {
30    ($($typename:ident),+) => {
31        impl<$($typename: Pattern),+> IntoPattern for ($($typename),+) {
32            type Pattern = tuple_into_cons_list!($($typename),+);
33
34            #[expect(non_snake_case)]
35            fn into_pattern(self) -> Self::Pattern {
36                let ($($typename),+) = self;
37                tuple_into_cons_list!($($typename),+)
38            }
39        }
40
41        impl_into_pattern_for_tuple!(continue $($typename),+);
42    };
43
44    (continue $_dropped:ident, $new_first:ident, $new_second:ident, $($more:ident),+) => {
45        impl_into_pattern_for_tuple!($new_first, $new_second, $($more),+);
46    };
47
48    (continue $_dropped:ident, $_new_first:ident, $_new_second:ident) => {};
49}
50
51impl_into_pattern_for_tuple!(T0, T1, T2, T3, T4, T5, T6, T7, T8, T9);
52