Skip to main content

winnow/combinator/
multi.rs

1//! Combinators applying their child parser multiple times
2
3use crate::combinator::trace;
4use crate::error::FromExternalError;
5use crate::error::ParserError;
6use crate::stream::Accumulate;
7use crate::stream::Range;
8use crate::stream::Stream;
9use crate::Parser;
10use crate::Result;
11
12/// Repeats the embedded parser, lazily returning the results
13///
14/// This can serve as a building block for custom parsers like [`repeat`].
15/// To iterate over all of the input in your application, see [`Parser::parse_iter`].
16///
17/// Call the iterator's [`ParserIterator::finish`] method to get the remaining input if successful,
18/// or the error value if we encountered an error.
19///
20/// On [`ErrMode::Backtrack`][crate::error::ErrMode::Backtrack], iteration will stop. To instead chain an error up, see [`cut_err`][crate::combinator::cut_err].
21///
22/// # Example
23///
24/// ```rust
25/// # #[cfg(feature = "ascii")] {
26/// # use winnow::prelude::*;
27/// # use winnow::Result;
28/// use winnow::{combinator::iterator, ascii::alpha1, combinator::terminated};
29/// use std::collections::HashMap;
30///
31/// let mut data = "abc|defg|hijkl|mnopqr|123";
32/// let mut it = iterator(&mut data, terminated(alpha1, "|"));
33///
34/// let parsed = it.map(|v| (v, v.len())).collect::<HashMap<_,_>>();
35/// let res: Result<_> = it.finish();
36///
37/// assert_eq!(parsed, [("abc", 3usize), ("defg", 4), ("hijkl", 5), ("mnopqr", 6)].iter().cloned().collect());
38/// assert_eq!(data, "123");
39/// # }
40/// ```
41pub fn iterator<Input, Output, Error, ParseNext>(
42    input: &mut Input,
43    parser: ParseNext,
44) -> ParserIterator<'_, ParseNext, Input, Output, Error>
45where
46    ParseNext: Parser<Input, Output, Error>,
47    Input: Stream,
48    Error: ParserError<Input>,
49{
50    ParserIterator {
51        parser,
52        input,
53        state: State::Running,
54        marker: Default::default(),
55    }
56}
57
58/// Main structure associated to [`iterator`].
59pub struct ParserIterator<'i, F, I, O, E>
60where
61    F: Parser<I, O, E>,
62    I: Stream,
63{
64    parser: F,
65    input: &'i mut I,
66    state: State<E>,
67    marker: core::marker::PhantomData<O>,
68}
69
70impl<F, I, O, E> ParserIterator<'_, F, I, O, E>
71where
72    F: Parser<I, O, E>,
73    I: Stream,
74    E: ParserError<I>,
75{
76    /// Returns the remaining input if parsing was successful, or the error if we encountered an error.
77    pub fn finish(self) -> Result<(), E> {
78        match self.state {
79            State::Running | State::Done => Ok(()),
80            State::Cut(e) => Err(e),
81        }
82    }
83}
84
85impl<F, I, O, E> core::iter::Iterator for &mut ParserIterator<'_, F, I, O, E>
86where
87    F: Parser<I, O, E>,
88    I: Stream,
89    E: ParserError<I>,
90{
91    type Item = O;
92
93    fn next(&mut self) -> Option<Self::Item> {
94        if matches!(self.state, State::Running) {
95            let start = self.input.checkpoint();
96
97            match self.parser.parse_next(self.input) {
98                Ok(o) => {
99                    self.state = State::Running;
100                    Some(o)
101                }
102                Err(e) if e.is_backtrack() => {
103                    self.input.reset(&start);
104                    self.state = State::Done;
105                    None
106                }
107                Err(e) => {
108                    self.state = State::Cut(e);
109                    None
110                }
111            }
112        } else {
113            None
114        }
115    }
116}
117
118enum State<E> {
119    Running,
120    Done,
121    Cut(E),
122}
123
124/// [`Accumulate`] the output of a parser into a container, like `Vec`
125///
126/// This stops before `n` when the parser returns [`ErrMode::Backtrack`][crate::error::ErrMode::Backtrack]. To instead chain an error up, see
127/// [`cut_err`][crate::combinator::cut_err].
128///
129/// To take a series of tokens, [`Accumulate`] into a `()`
130/// (e.g. with [`.map(|()| ())`][Parser::map])
131/// and then [`Parser::take`].
132///
133/// <div class="warning">
134///
135/// **Warning:** If the parser passed to `repeat` accepts empty inputs
136/// (like `alpha0` or `digit0`), `repeat` will return an error,
137/// to prevent going into an infinite loop.
138///
139/// </div>
140///
141/// # Example
142///
143/// Zero or more repetitions:
144/// ```rust
145/// # #[cfg(feature = "std")] {
146/// # use winnow::{error::ErrMode, error::Needed};
147/// # use winnow::prelude::*;
148/// use winnow::combinator::repeat;
149///
150/// fn parser<'i>(s: &mut &'i str) -> ModalResult<Vec<&'i str>> {
151///   repeat(0.., "abc").parse_next(s)
152/// }
153///
154/// assert_eq!(parser.parse_peek("abcabc"), Ok(("", vec!["abc", "abc"])));
155/// assert_eq!(parser.parse_peek("abc123"), Ok(("123", vec!["abc"])));
156/// assert_eq!(parser.parse_peek("123123"), Ok(("123123", vec![])));
157/// assert_eq!(parser.parse_peek(""), Ok(("", vec![])));
158/// # }
159/// ```
160///
161/// One or more repetitions:
162/// ```rust
163/// # #[cfg(feature = "std")] {
164/// # use winnow::{error::ErrMode, error::Needed};
165/// # use winnow::prelude::*;
166/// use winnow::combinator::repeat;
167///
168/// fn parser<'i>(s: &mut &'i str) -> ModalResult<Vec<&'i str>> {
169///   repeat(1.., "abc").parse_next(s)
170/// }
171///
172/// assert_eq!(parser.parse_peek("abcabc"), Ok(("", vec!["abc", "abc"])));
173/// assert_eq!(parser.parse_peek("abc123"), Ok(("123", vec!["abc"])));
174/// assert!(parser.parse_peek("123123").is_err());
175/// assert!(parser.parse_peek("").is_err());
176/// # }
177/// ```
178///
179/// Fixed number of repetitions:
180/// ```rust
181/// # #[cfg(feature = "std")] {
182/// # use winnow::{error::ErrMode, error::Needed};
183/// # use winnow::prelude::*;
184/// use winnow::combinator::repeat;
185///
186/// fn parser<'i>(s: &mut &'i str) -> ModalResult<Vec<&'i str>> {
187///   repeat(2, "abc").parse_next(s)
188/// }
189///
190/// assert_eq!(parser.parse_peek("abcabc"), Ok(("", vec!["abc", "abc"])));
191/// assert!(parser.parse_peek("abc123").is_err());
192/// assert!(parser.parse_peek("123123").is_err());
193/// assert!(parser.parse_peek("").is_err());
194/// assert_eq!(parser.parse_peek("abcabcabc"), Ok(("abc", vec!["abc", "abc"])));
195/// # }
196/// ```
197///
198/// Arbitrary repetitions:
199/// ```rust
200/// # #[cfg(feature = "std")] {
201/// # use winnow::{error::ErrMode, error::Needed};
202/// # use winnow::prelude::*;
203/// use winnow::combinator::repeat;
204///
205/// fn parser<'i>(s: &mut &'i str) -> ModalResult<Vec<&'i str>> {
206///   repeat(0..=2, "abc").parse_next(s)
207/// }
208///
209/// assert_eq!(parser.parse_peek("abcabc"), Ok(("", vec!["abc", "abc"])));
210/// assert_eq!(parser.parse_peek("abc123"), Ok(("123", vec!["abc"])));
211/// assert_eq!(parser.parse_peek("123123"), Ok(("123123", vec![])));
212/// assert_eq!(parser.parse_peek(""), Ok(("", vec![])));
213/// assert_eq!(parser.parse_peek("abcabcabc"), Ok(("abc", vec!["abc", "abc"])));
214/// # }
215/// ```
216#[doc(alias = "many0")]
217#[doc(alias = "count")]
218#[doc(alias = "many0_count")]
219#[doc(alias = "many1")]
220#[doc(alias = "many1_count")]
221#[doc(alias = "many_m_n")]
222#[doc(alias = "repeated")]
223#[doc(alias = "skip_many")]
224#[doc(alias = "skip_many1")]
225#[inline(always)]
226pub fn repeat<Input, Output, Accumulator, Error, ParseNext>(
227    occurrences: impl Into<Range>,
228    parser: ParseNext,
229) -> Repeat<ParseNext, Input, Output, Accumulator, Error>
230where
231    Input: Stream,
232    Accumulator: Accumulate<Output>,
233    ParseNext: Parser<Input, Output, Error>,
234    Error: ParserError<Input>,
235{
236    Repeat {
237        occurrences: occurrences.into(),
238        parser,
239        marker: Default::default(),
240    }
241}
242
243/// Customizable [`Parser`] implementation for [`repeat`]
244pub struct Repeat<P, I, O, C, E>
245where
246    P: Parser<I, O, E>,
247    I: Stream,
248    C: Accumulate<O>,
249    E: ParserError<I>,
250{
251    occurrences: Range,
252    parser: P,
253    marker: core::marker::PhantomData<(I, O, C, E)>,
254}
255
256impl<ParseNext, Input, Output, Error> Repeat<ParseNext, Input, Output, (), Error>
257where
258    ParseNext: Parser<Input, Output, Error>,
259    Input: Stream,
260    Error: ParserError<Input>,
261{
262    /// Repeats the embedded parser, calling `op` to gather the results
263    ///
264    /// This stops before `n` when the parser returns [`ErrMode::Backtrack`][crate::error::ErrMode::Backtrack]. To instead chain an error up, see
265    /// [`cut_err`][crate::combinator::cut_err].
266    ///
267    /// # Arguments
268    /// * `init` A function returning the initial value.
269    /// * `op` The function that combines a result of `f` with
270    ///   the current accumulator.
271    ///
272    /// <div class="warning">
273    ///
274    /// **Warning:** If the parser passed to [`repeat`] accepts empty inputs
275    /// (like `alpha0` or `digit0`), `fold` will return an error,
276    /// to prevent going into an infinite loop.
277    ///
278    /// </div>
279    ///
280    /// # Example
281    ///
282    /// Zero or more repetitions:
283    /// ```rust
284    /// # use winnow::{error::ErrMode, error::Needed};
285    /// # use winnow::prelude::*;
286    /// use winnow::combinator::repeat;
287    ///
288    /// fn parser<'i>(s: &mut &'i str) -> ModalResult<Vec<&'i str>> {
289    ///   repeat(
290    ///     0..,
291    ///     "abc"
292    ///   ).fold(
293    ///     Vec::new,
294    ///     |mut acc: Vec<_>, item| {
295    ///       acc.push(item);
296    ///       acc
297    ///     }
298    ///   ).parse_next(s)
299    /// }
300    ///
301    /// assert_eq!(parser.parse_peek("abcabc"), Ok(("", vec!["abc", "abc"])));
302    /// assert_eq!(parser.parse_peek("abc123"), Ok(("123", vec!["abc"])));
303    /// assert_eq!(parser.parse_peek("123123"), Ok(("123123", vec![])));
304    /// assert_eq!(parser.parse_peek(""), Ok(("", vec![])));
305    /// ```
306    ///
307    /// One or more repetitions:
308    /// ```rust
309    /// # use winnow::{error::ErrMode, error::Needed};
310    /// # use winnow::prelude::*;
311    /// use winnow::combinator::repeat;
312    ///
313    /// fn parser<'i>(s: &mut &'i str) -> ModalResult<Vec<&'i str>> {
314    ///   repeat(
315    ///     1..,
316    ///     "abc",
317    ///   ).fold(
318    ///     Vec::new,
319    ///     |mut acc: Vec<_>, item| {
320    ///       acc.push(item);
321    ///       acc
322    ///     }
323    ///   ).parse_next(s)
324    /// }
325    ///
326    /// assert_eq!(parser.parse_peek("abcabc"), Ok(("", vec!["abc", "abc"])));
327    /// assert_eq!(parser.parse_peek("abc123"), Ok(("123", vec!["abc"])));
328    /// assert!(parser.parse_peek("123123").is_err());
329    /// assert!(parser.parse_peek("").is_err());
330    /// ```
331    ///
332    /// Arbitrary number of repetitions:
333    /// ```rust
334    /// # use winnow::{error::ErrMode, error::Needed};
335    /// # use winnow::prelude::*;
336    /// use winnow::combinator::repeat;
337    ///
338    /// fn parser<'i>(s: &mut &'i str) -> ModalResult<Vec<&'i str>> {
339    ///   repeat(
340    ///     0..=2,
341    ///     "abc",
342    ///   ).fold(
343    ///     Vec::new,
344    ///     |mut acc: Vec<_>, item| {
345    ///       acc.push(item);
346    ///       acc
347    ///     }
348    ///   ).parse_next(s)
349    /// }
350    ///
351    /// assert_eq!(parser.parse_peek("abcabc"), Ok(("", vec!["abc", "abc"])));
352    /// assert_eq!(parser.parse_peek("abc123"), Ok(("123", vec!["abc"])));
353    /// assert_eq!(parser.parse_peek("123123"), Ok(("123123", vec![])));
354    /// assert_eq!(parser.parse_peek(""), Ok(("", vec![])));
355    /// assert_eq!(parser.parse_peek("abcabcabc"), Ok(("abc", vec!["abc", "abc"])));
356    /// ```
357    #[doc(alias = "fold_many0")]
358    #[doc(alias = "fold_many1")]
359    #[doc(alias = "fold_many_m_n")]
360    #[doc(alias = "fold_repeat")]
361    #[inline(always)]
362    pub fn fold<Init, Op, Result>(
363        mut self,
364        mut init: Init,
365        mut op: Op,
366    ) -> impl Parser<Input, Result, Error>
367    where
368        Init: FnMut() -> Result,
369        Op: FnMut(Result, Output) -> Result,
370    {
371        let Range {
372            start_inclusive,
373            end_inclusive,
374        } = self.occurrences;
375        trace("repeat_fold", move |i: &mut Input| {
376            match (start_inclusive, end_inclusive) {
377                (0, None) => fold_repeat0_(&mut self.parser, &mut init, &mut op, i),
378                (1, None) => fold_repeat1_(&mut self.parser, &mut init, &mut op, i),
379                (start, end) if Some(start) == end => {
380                    fold_repeat_n_(start, &mut self.parser, &mut init, &mut op, i)
381                }
382                (start, end) => fold_repeat_m_n_(
383                    start,
384                    end.unwrap_or(usize::MAX),
385                    &mut self.parser,
386                    &mut init,
387                    &mut op,
388                    i,
389                ),
390            }
391        })
392    }
393
394    /// Akin to [`Repeat::fold`], but for containers that can reject an element.
395    ///
396    /// This stops before `n` when the parser returns [`ErrMode::Backtrack`][crate::error::ErrMode::Backtrack]. To instead chain an error up, see
397    /// [`cut_err`][crate::combinator::cut_err]. Additionally, if the fold function returns `None`, the parser will
398    /// stop and return an error.
399    ///
400    /// # Arguments
401    /// * `init` A function returning the initial value.
402    /// * `op` The function that combines a result of `f` with
403    ///   the current accumulator.
404    ///
405    /// <div class="warning">
406    ///
407    /// **Warning:** If the parser passed to [`repeat`] accepts empty inputs
408    /// (like `alpha0` or `digit0`), `verify_fold` will return an error,
409    /// to prevent going into an infinite loop.
410    ///
411    /// </div>
412    ///
413    /// # Example
414    ///
415    /// Guaranteeing that the input had unique elements:
416    /// ```rust
417    /// # use winnow::{error::ErrMode, error::Needed};
418    /// # use winnow::prelude::*;
419    /// use winnow::combinator::repeat;
420    /// use std::collections::HashSet;
421    ///
422    /// fn parser<'i>(s: &mut &'i str) -> ModalResult<HashSet<&'i str>> {
423    ///   repeat(
424    ///     0..,
425    ///     "abc"
426    ///   ).verify_fold(
427    ///     HashSet::new,
428    ///     |mut acc: HashSet<_>, item| {
429    ///       if acc.insert(item) {
430    ///          Some(acc)
431    ///       } else {
432    ///          None
433    ///       }
434    ///     }
435    ///   ).parse_next(s)
436    /// }
437    ///
438    /// assert_eq!(parser.parse_peek("abc"), Ok(("", HashSet::from(["abc"]))));
439    /// assert!(parser.parse_peek("abcabc").is_err());
440    /// assert_eq!(parser.parse_peek("abc123"), Ok(("123", HashSet::from(["abc"]))));
441    /// assert_eq!(parser.parse_peek("123123"), Ok(("123123", HashSet::from([]))));
442    /// assert_eq!(parser.parse_peek(""), Ok(("", HashSet::from([]))));
443    /// ```
444    #[inline(always)]
445    pub fn verify_fold<Init, Op, Result>(
446        mut self,
447        mut init: Init,
448        mut op: Op,
449    ) -> impl Parser<Input, Result, Error>
450    where
451        Init: FnMut() -> Result,
452        Op: FnMut(Result, Output) -> Option<Result>,
453    {
454        let Range {
455            start_inclusive,
456            end_inclusive,
457        } = self.occurrences;
458        trace("repeat_verify_fold", move |input: &mut Input| {
459            verify_fold_m_n(
460                start_inclusive,
461                end_inclusive.unwrap_or(usize::MAX),
462                &mut self.parser,
463                &mut init,
464                &mut op,
465                input,
466            )
467        })
468    }
469
470    /// Akin to [`Repeat::fold`], but for containers that can error when an element is accumulated.
471    ///
472    /// This stops before `n` when the parser returns [`ErrMode::Backtrack`][crate::error::ErrMode::Backtrack]. To instead chain an error up, see
473    /// [`cut_err`][crate::combinator::cut_err]. Additionally, if the fold function returns an error, the parser will
474    /// stop and return it.
475    ///
476    /// # Arguments
477    /// * `init` A function returning the initial value.
478    /// * `op` The function that combines a result of `f` with
479    ///   the current accumulator.
480    ///
481    /// <div class="warning">
482    ///
483    /// **Warning:** If the parser passed to [`repeat`] accepts empty inputs
484    /// (like `alpha0` or `digit0`), `try_fold` will return an error,
485    /// to prevent going into an infinite loop.
486    ///
487    /// </div>
488    ///
489    /// # Example
490    ///
491    /// Writing the output to a vector of bytes:
492    /// ```rust
493    /// # use winnow::{error::ErrMode, error::Needed};
494    /// # use winnow::prelude::*;
495    /// use winnow::combinator::repeat;
496    /// use std::io::Write;
497    /// use std::io::Error;
498    ///
499    /// fn parser(s: &mut &str) -> ModalResult<Vec<u8>> {
500    ///   repeat(
501    ///     0..,
502    ///     "abc"
503    ///   ).try_fold(
504    ///     Vec::new,
505    ///     |mut acc, item: &str| -> Result<_, Error> {
506    ///       acc.write(item.as_bytes())?;
507    ///       Ok(acc)
508    ///     }
509    ///   ).parse_next(s)
510    /// }
511    ///
512    /// assert_eq!(parser.parse_peek("abc"), Ok(("", b"abc".to_vec())));
513    /// assert_eq!(parser.parse_peek("abc123"), Ok(("123", b"abc".to_vec())));
514    /// assert_eq!(parser.parse_peek("123123"), Ok(("123123", vec![])));
515    /// assert_eq!(parser.parse_peek(""), Ok(("", vec![])));
516    #[inline(always)]
517    pub fn try_fold<Init, Op, OpError, Result>(
518        mut self,
519        mut init: Init,
520        mut op: Op,
521    ) -> impl Parser<Input, Result, Error>
522    where
523        Init: FnMut() -> Result,
524        Op: FnMut(Result, Output) -> core::result::Result<Result, OpError>,
525        Error: FromExternalError<Input, OpError>,
526    {
527        let Range {
528            start_inclusive,
529            end_inclusive,
530        } = self.occurrences;
531        trace("repeat_try_fold", move |input: &mut Input| {
532            try_fold_m_n(
533                start_inclusive,
534                end_inclusive.unwrap_or(usize::MAX),
535                &mut self.parser,
536                &mut init,
537                &mut op,
538                input,
539            )
540        })
541    }
542}
543
544impl<P, I, O, C, E> Parser<I, C, E> for Repeat<P, I, O, C, E>
545where
546    P: Parser<I, O, E>,
547    I: Stream,
548    C: Accumulate<O>,
549    E: ParserError<I>,
550{
551    #[inline(always)]
552    fn parse_next(&mut self, i: &mut I) -> Result<C, E> {
553        let Range {
554            start_inclusive,
555            end_inclusive,
556        } = self.occurrences;
557        trace("repeat", move |i: &mut I| {
558            match (start_inclusive, end_inclusive) {
559                (0, None) => fold_repeat0_(
560                    &mut self.parser,
561                    &mut || C::initial(None),
562                    &mut |mut acc, o| {
563                        acc.accumulate(o);
564                        acc
565                    },
566                    i,
567                ),
568                (1, None) => fold_repeat1_(
569                    &mut self.parser,
570                    &mut || C::initial(None),
571                    &mut |mut acc, o| {
572                        acc.accumulate(o);
573                        acc
574                    },
575                    i,
576                ),
577                (min, end) if Some(min) == end => fold_repeat_n_(
578                    min,
579                    &mut self.parser,
580                    &mut || C::initial(Some(min)),
581                    &mut |mut acc, o| {
582                        acc.accumulate(o);
583                        acc
584                    },
585                    i,
586                ),
587                (min, end) => fold_repeat_m_n_(
588                    min,
589                    end.unwrap_or(usize::MAX),
590                    &mut self.parser,
591                    &mut || C::initial(Some(min)),
592                    &mut |mut acc, o| {
593                        acc.accumulate(o);
594                        acc
595                    },
596                    i,
597                ),
598            }
599        })
600        .parse_next(i)
601    }
602}
603
604fn fold_repeat0_<I, O, E, P, N, F, R>(
605    parser: &mut P,
606    init: &mut N,
607    fold: &mut F,
608    input: &mut I,
609) -> Result<R, E>
610where
611    I: Stream,
612    P: Parser<I, O, E>,
613    N: FnMut() -> R,
614    F: FnMut(R, O) -> R,
615    E: ParserError<I>,
616{
617    let mut res = init();
618
619    loop {
620        let start = input.checkpoint();
621        let len = input.eof_offset();
622        match parser.parse_next(input) {
623            Ok(output) => {
624                // infinite loop check: the parser must always consume
625                if input.eof_offset() == len {
626                    return Err(ParserError::assert(
627                        input,
628                        "`repeat` parsers must always consume",
629                    ));
630                }
631
632                res = fold(res, output);
633            }
634            Err(err) if err.is_backtrack() => {
635                input.reset(&start);
636                return Ok(res);
637            }
638            Err(err) => {
639                return Err(err);
640            }
641        }
642    }
643}
644
645fn fold_repeat1_<I, O, E, P, N, F, R>(
646    parser: &mut P,
647    init: &mut N,
648    fold: &mut F,
649    input: &mut I,
650) -> Result<R, E>
651where
652    I: Stream,
653    P: Parser<I, O, E>,
654    N: FnMut() -> R,
655    F: FnMut(R, O) -> R,
656    E: ParserError<I>,
657{
658    let start = input.checkpoint();
659    match parser.parse_next(input) {
660        Err(err) => Err(err.append(input, &start)),
661        Ok(output) => {
662            let init = init();
663            let mut res = fold(init, output);
664
665            loop {
666                let start = input.checkpoint();
667                let len = input.eof_offset();
668                match parser.parse_next(input) {
669                    Err(err) if err.is_backtrack() => {
670                        input.reset(&start);
671                        break;
672                    }
673                    Err(err) => return Err(err),
674                    Ok(output) => {
675                        // infinite loop check: the parser must always consume
676                        if input.eof_offset() == len {
677                            return Err(ParserError::assert(
678                                input,
679                                "`repeat` parsers must always consume",
680                            ));
681                        }
682
683                        res = fold(res, output);
684                    }
685                }
686            }
687
688            Ok(res)
689        }
690    }
691}
692
693fn fold_repeat_n_<I, O, E, P, N, F, R>(
694    count: usize,
695    parse: &mut P,
696    init: &mut N,
697    fold: &mut F,
698    input: &mut I,
699) -> Result<R, E>
700where
701    I: Stream,
702    P: Parser<I, O, E>,
703    N: FnMut() -> R,
704    F: FnMut(R, O) -> R,
705    E: ParserError<I>,
706{
707    let mut res = init();
708
709    for _ in 0..count {
710        let start = input.checkpoint();
711        let len = input.eof_offset();
712        match parse.parse_next(input) {
713            Ok(output) => {
714                // infinite loop check: the parser must always consume
715                if input.eof_offset() == len {
716                    return Err(ParserError::assert(
717                        input,
718                        "`repeat` parsers must always consume",
719                    ));
720                }
721
722                res = fold(res, output);
723            }
724            Err(err) => {
725                return Err(err.append(input, &start));
726            }
727        }
728    }
729
730    Ok(res)
731}
732
733fn fold_repeat_m_n_<I, O, E, P, N, F, R>(
734    min: usize,
735    max: usize,
736    parse: &mut P,
737    init: &mut N,
738    fold: &mut F,
739    input: &mut I,
740) -> Result<R, E>
741where
742    I: Stream,
743    P: Parser<I, O, E>,
744    N: FnMut() -> R,
745    F: FnMut(R, O) -> R,
746    E: ParserError<I>,
747{
748    if min > max {
749        return Err(ParserError::assert(
750            input,
751            "range should be ascending, rather than descending",
752        ));
753    }
754
755    let mut res = init();
756    for count in 0..max {
757        let start = input.checkpoint();
758        let len = input.eof_offset();
759        match parse.parse_next(input) {
760            Ok(output) => {
761                // infinite loop check: the parser must always consume
762                if input.eof_offset() == len {
763                    return Err(ParserError::assert(
764                        input,
765                        "`repeat` parsers must always consume",
766                    ));
767                }
768
769                res = fold(res, output);
770            }
771            //FInputXMError: handle failure properly
772            Err(err) if err.is_backtrack() => {
773                if count < min {
774                    return Err(err.append(input, &start));
775                } else {
776                    input.reset(&start);
777                    break;
778                }
779            }
780            Err(err) => return Err(err),
781        }
782    }
783
784    Ok(res)
785}
786
787fn verify_fold_m_n<I, O, E, P, N, F, R>(
788    min: usize,
789    max: usize,
790    parse: &mut P,
791    init: &mut N,
792    fold: &mut F,
793    input: &mut I,
794) -> Result<R, E>
795where
796    I: Stream,
797    P: Parser<I, O, E>,
798    N: FnMut() -> R,
799    F: FnMut(R, O) -> Option<R>,
800    E: ParserError<I>,
801{
802    if min > max {
803        return Err(ParserError::assert(
804            input,
805            "range should be ascending, rather than descending",
806        ));
807    }
808
809    let mut res = init();
810    for count in 0..max {
811        let start = input.checkpoint();
812        let len = input.eof_offset();
813        match parse.parse_next(input) {
814            Ok(output) => {
815                // infinite loop check: the parser must always consume
816                if input.eof_offset() == len {
817                    return Err(ParserError::assert(
818                        input,
819                        "`repeat` parsers must always consume",
820                    ));
821                }
822
823                let Some(res_) = fold(res, output) else {
824                    input.reset(&start);
825                    let res = Err(ParserError::from_input(input));
826                    super::debug::trace_result("verify_fold", &res);
827                    return res;
828                };
829                res = res_;
830            }
831            //FInputXMError: handle failure properly
832            Err(err) if err.is_backtrack() => {
833                if count < min {
834                    return Err(err.append(input, &start));
835                } else {
836                    input.reset(&start);
837                    break;
838                }
839            }
840            Err(err) => return Err(err),
841        }
842    }
843
844    Ok(res)
845}
846
847fn try_fold_m_n<I, O, E, P, N, F, R, RE>(
848    min: usize,
849    max: usize,
850    parse: &mut P,
851    init: &mut N,
852    fold: &mut F,
853    input: &mut I,
854) -> Result<R, E>
855where
856    I: Stream,
857    P: Parser<I, O, E>,
858    N: FnMut() -> R,
859    F: FnMut(R, O) -> Result<R, RE>,
860    E: ParserError<I> + FromExternalError<I, RE>,
861{
862    if min > max {
863        return Err(ParserError::assert(
864            input,
865            "range should be ascending, rather than descending",
866        ));
867    }
868
869    let mut res = init();
870    for count in 0..max {
871        let start = input.checkpoint();
872        let len = input.eof_offset();
873        match parse.parse_next(input) {
874            Ok(output) => {
875                // infinite loop check: the parser must always consume
876                if input.eof_offset() == len {
877                    return Err(ParserError::assert(
878                        input,
879                        "`repeat` parsers must always consume",
880                    ));
881                }
882
883                match fold(res, output) {
884                    Ok(res_) => res = res_,
885                    Err(err) => {
886                        input.reset(&start);
887                        let res = Err(E::from_external_error(input, err));
888                        super::debug::trace_result("try_fold", &res);
889                        return res;
890                    }
891                }
892            }
893            //FInputXMError: handle failure properly
894            Err(err) if err.is_backtrack() => {
895                if count < min {
896                    return Err(err.append(input, &start));
897                } else {
898                    input.reset(&start);
899                    break;
900                }
901            }
902            Err(err) => return Err(err),
903        }
904    }
905
906    Ok(res)
907}
908
909/// [`Accumulate`] the output of parser `f` into a container, like `Vec`, until the parser `g`
910/// produces a result.
911///
912/// Returns a tuple of the results of `f` in a `Vec` and the result of `g`.
913///
914/// `f` keeps going so long as `g` produces [`ErrMode::Backtrack`][crate::error::ErrMode::Backtrack]. To instead chain an error up, see [`cut_err`][crate::combinator::cut_err].
915///
916/// To take a series of tokens, [`Accumulate`] into a `()`
917/// (e.g. with [`.map(|((), _)| ())`][Parser::map])
918/// and then [`Parser::take`].
919///
920/// See also
921/// - [`take_till`][crate::token::take_till] for recognizing up-to a member of a [set of tokens][crate::stream::ContainsToken]
922/// - [`take_until`][crate::token::take_until] for recognizing up-to a [`literal`][crate::token::literal] (w/ optional simd optimizations)
923///
924/// # Example
925///
926/// ```rust
927/// # #[cfg(feature = "std")] {
928/// # use winnow::{error::ErrMode, error::Needed};
929/// # use winnow::prelude::*;
930/// use winnow::combinator::repeat_till;
931///
932/// fn parser<'i>(s: &mut &'i str) -> ModalResult<(Vec<&'i str>, &'i str)> {
933///   repeat_till(0.., "abc", "end").parse_next(s)
934/// };
935///
936/// assert_eq!(parser.parse_peek("abcabcend"), Ok(("", (vec!["abc", "abc"], "end"))));
937/// assert!(parser.parse_peek("abc123end").is_err());
938/// assert!(parser.parse_peek("123123end").is_err());
939/// assert!(parser.parse_peek("").is_err());
940/// assert_eq!(parser.parse_peek("abcendefg"), Ok(("efg", (vec!["abc"], "end"))));
941/// # }
942/// ```
943#[doc(alias = "many_till0")]
944pub fn repeat_till<Input, Output, Accumulator, Terminator, Error, ParseNext, TerminatorParser>(
945    occurrences: impl Into<Range>,
946    mut parse: ParseNext,
947    mut terminator: TerminatorParser,
948) -> impl Parser<Input, (Accumulator, Terminator), Error>
949where
950    Input: Stream,
951    Accumulator: Accumulate<Output>,
952    ParseNext: Parser<Input, Output, Error>,
953    TerminatorParser: Parser<Input, Terminator, Error>,
954    Error: ParserError<Input>,
955{
956    let Range {
957        start_inclusive,
958        end_inclusive,
959    } = occurrences.into();
960    trace("repeat_till", move |i: &mut Input| {
961        match (start_inclusive, end_inclusive) {
962            (0, None) => repeat_till0_(&mut parse, &mut terminator, i),
963            (start, end) => repeat_till_m_n_(
964                start,
965                end.unwrap_or(usize::MAX),
966                &mut parse,
967                &mut terminator,
968                i,
969            ),
970        }
971    })
972}
973
974fn repeat_till0_<I, O, C, P, E, F, G>(f: &mut F, g: &mut G, i: &mut I) -> Result<(C, P), E>
975where
976    I: Stream,
977    C: Accumulate<O>,
978    F: Parser<I, O, E>,
979    G: Parser<I, P, E>,
980    E: ParserError<I>,
981{
982    let mut res = C::initial(None);
983    loop {
984        let start = i.checkpoint();
985        let len = i.eof_offset();
986        match g.parse_next(i) {
987            Ok(o) => return Ok((res, o)),
988            Err(e) if e.is_backtrack() => {
989                i.reset(&start);
990                match f.parse_next(i) {
991                    Err(e) => return Err(e.append(i, &start)),
992                    Ok(o) => {
993                        // infinite loop check: the parser must always consume
994                        if i.eof_offset() == len {
995                            return Err(ParserError::assert(
996                                i,
997                                "`repeat` parsers must always consume",
998                            ));
999                        }
1000
1001                        res.accumulate(o);
1002                    }
1003                }
1004            }
1005            Err(e) => return Err(e),
1006        }
1007    }
1008}
1009
1010fn repeat_till_m_n_<I, O, C, P, E, F, G>(
1011    min: usize,
1012    max: usize,
1013    f: &mut F,
1014    g: &mut G,
1015    i: &mut I,
1016) -> Result<(C, P), E>
1017where
1018    I: Stream,
1019    C: Accumulate<O>,
1020    F: Parser<I, O, E>,
1021    G: Parser<I, P, E>,
1022    E: ParserError<I>,
1023{
1024    if min > max {
1025        return Err(ParserError::assert(
1026            i,
1027            "range should be ascending, rather than descending",
1028        ));
1029    }
1030
1031    let mut res = C::initial(Some(min));
1032
1033    let start = i.checkpoint();
1034    for _ in 0..min {
1035        match f.parse_next(i) {
1036            Ok(o) => {
1037                res.accumulate(o);
1038            }
1039            Err(e) => {
1040                return Err(e.append(i, &start));
1041            }
1042        }
1043    }
1044    for count in min..=max {
1045        let start = i.checkpoint();
1046        let len = i.eof_offset();
1047        match g.parse_next(i) {
1048            Ok(o) => return Ok((res, o)),
1049            Err(err) if err.is_backtrack() => {
1050                if count == max {
1051                    return Err(err);
1052                }
1053                i.reset(&start);
1054                match f.parse_next(i) {
1055                    Err(e) => {
1056                        return Err(e.append(i, &start));
1057                    }
1058                    Ok(o) => {
1059                        // infinite loop check: the parser must always consume
1060                        if i.eof_offset() == len {
1061                            return Err(ParserError::assert(
1062                                i,
1063                                "`repeat` parsers must always consume",
1064                            ));
1065                        }
1066
1067                        res.accumulate(o);
1068                    }
1069                }
1070            }
1071            Err(e) => return Err(e),
1072        }
1073    }
1074    unreachable!()
1075}
1076
1077/// [`Accumulate`] the output of a parser, interleaved with `sep`
1078///
1079/// This stops when either parser returns [`ErrMode::Backtrack`][crate::error::ErrMode::Backtrack]. To instead chain an error up, see
1080/// [`cut_err`][crate::combinator::cut_err].
1081///
1082/// To take a series of tokens, [`Accumulate`] into a `()`
1083/// (e.g. with [`.map(|()| ())`][Parser::map])
1084/// and then [`Parser::take`].
1085///
1086/// <div class="warning">
1087///
1088/// **Warning:** If the separator parser accepts empty inputs
1089/// (like `alpha0` or `digit0`), `separated` will return an error,
1090/// to prevent going into an infinite loop.
1091///
1092/// </div>
1093///
1094/// # Example
1095///
1096/// Zero or more repetitions:
1097/// ```rust
1098/// # #[cfg(feature = "std")] {
1099/// # use winnow::{error::ErrMode, error::Needed};
1100/// # use winnow::prelude::*;
1101/// use winnow::combinator::separated;
1102///
1103/// fn parser<'i>(s: &mut &'i str) -> ModalResult<Vec<&'i str>> {
1104///   separated(0.., "abc", "|").parse_next(s)
1105/// }
1106///
1107/// assert_eq!(parser.parse_peek("abc|abc|abc"), Ok(("", vec!["abc", "abc", "abc"])));
1108/// assert_eq!(parser.parse_peek("abc123abc"), Ok(("123abc", vec!["abc"])));
1109/// assert_eq!(parser.parse_peek("abc|def"), Ok(("|def", vec!["abc"])));
1110/// assert_eq!(parser.parse_peek(""), Ok(("", vec![])));
1111/// assert_eq!(parser.parse_peek("def|abc"), Ok(("def|abc", vec![])));
1112/// # }
1113/// ```
1114///
1115/// One or more repetitions:
1116/// ```rust
1117/// # #[cfg(feature = "std")] {
1118/// # use winnow::{error::ErrMode, error::Needed};
1119/// # use winnow::prelude::*;
1120/// use winnow::combinator::separated;
1121///
1122/// fn parser<'i>(s: &mut &'i str) -> ModalResult<Vec<&'i str>> {
1123///   separated(1.., "abc", "|").parse_next(s)
1124/// }
1125///
1126/// assert_eq!(parser.parse_peek("abc|abc|abc"), Ok(("", vec!["abc", "abc", "abc"])));
1127/// assert_eq!(parser.parse_peek("abc123abc"), Ok(("123abc", vec!["abc"])));
1128/// assert_eq!(parser.parse_peek("abc|def"), Ok(("|def", vec!["abc"])));
1129/// assert!(parser.parse_peek("").is_err());
1130/// assert!(parser.parse_peek("def|abc").is_err());
1131/// # }
1132/// ```
1133///
1134/// Fixed number of repetitions:
1135/// ```rust
1136/// # #[cfg(feature = "std")] {
1137/// # use winnow::{error::ErrMode, error::Needed};
1138/// # use winnow::prelude::*;
1139/// use winnow::combinator::separated;
1140///
1141/// fn parser<'i>(s: &mut &'i str) -> ModalResult<Vec<&'i str>> {
1142///   separated(2, "abc", "|").parse_next(s)
1143/// }
1144///
1145/// assert_eq!(parser.parse_peek("abc|abc|abc"), Ok(("|abc", vec!["abc", "abc"])));
1146/// assert!(parser.parse_peek("abc123abc").is_err());
1147/// assert!(parser.parse_peek("abc|def").is_err());
1148/// assert!(parser.parse_peek("").is_err());
1149/// assert!(parser.parse_peek("def|abc").is_err());
1150/// # }
1151/// ```
1152///
1153/// Arbitrary repetitions:
1154/// ```rust
1155/// # #[cfg(feature = "std")] {
1156/// # use winnow::{error::ErrMode, error::Needed};
1157/// # use winnow::prelude::*;
1158/// use winnow::combinator::separated;
1159///
1160/// fn parser<'i>(s: &mut &'i str) -> ModalResult<Vec<&'i str>> {
1161///   separated(0..=2, "abc", "|").parse_next(s)
1162/// }
1163///
1164/// assert_eq!(parser.parse_peek("abc|abc|abc"), Ok(("|abc", vec!["abc", "abc"])));
1165/// assert_eq!(parser.parse_peek("abc123abc"), Ok(("123abc", vec!["abc"])));
1166/// assert_eq!(parser.parse_peek("abc|def"), Ok(("|def", vec!["abc"])));
1167/// assert_eq!(parser.parse_peek(""), Ok(("", vec![])));
1168/// assert_eq!(parser.parse_peek("def|abc"), Ok(("def|abc", vec![])));
1169/// # }
1170/// ```
1171#[doc(alias = "sep_by")]
1172#[doc(alias = "sep_by1")]
1173#[doc(alias = "separated_list0")]
1174#[doc(alias = "separated_list1")]
1175#[doc(alias = "separated_m_n")]
1176#[inline(always)]
1177pub fn separated<Input, Output, Accumulator, Sep, Error, ParseNext, SepParser>(
1178    occurrences: impl Into<Range>,
1179    mut parser: ParseNext,
1180    mut separator: SepParser,
1181) -> impl Parser<Input, Accumulator, Error>
1182where
1183    Input: Stream,
1184    Accumulator: Accumulate<Output>,
1185    ParseNext: Parser<Input, Output, Error>,
1186    SepParser: Parser<Input, Sep, Error>,
1187    Error: ParserError<Input>,
1188{
1189    let Range {
1190        start_inclusive,
1191        end_inclusive,
1192    } = occurrences.into();
1193    trace("separated", move |input: &mut Input| {
1194        match (start_inclusive, end_inclusive) {
1195            (0, None) => separated0_(&mut parser, &mut separator, input),
1196            (1, None) => separated1_(&mut parser, &mut separator, input),
1197            (start, end) if Some(start) == end => {
1198                separated_n_(start, &mut parser, &mut separator, input)
1199            }
1200            (start, end) => separated_m_n_(
1201                start,
1202                end.unwrap_or(usize::MAX),
1203                &mut parser,
1204                &mut separator,
1205                input,
1206            ),
1207        }
1208    })
1209}
1210
1211fn separated0_<I, O, C, O2, E, P, S>(
1212    parser: &mut P,
1213    separator: &mut S,
1214    input: &mut I,
1215) -> Result<C, E>
1216where
1217    I: Stream,
1218    C: Accumulate<O>,
1219    P: Parser<I, O, E>,
1220    S: Parser<I, O2, E>,
1221    E: ParserError<I>,
1222{
1223    let mut acc = C::initial(None);
1224
1225    let start = input.checkpoint();
1226    match parser.parse_next(input) {
1227        Err(e) if e.is_backtrack() => {
1228            input.reset(&start);
1229            return Ok(acc);
1230        }
1231        Err(e) => return Err(e),
1232        Ok(o) => {
1233            acc.accumulate(o);
1234        }
1235    }
1236
1237    loop {
1238        let start = input.checkpoint();
1239        let len = input.eof_offset();
1240        match separator.parse_next(input) {
1241            Err(e) if e.is_backtrack() => {
1242                input.reset(&start);
1243                return Ok(acc);
1244            }
1245            Err(e) => return Err(e),
1246            Ok(_) => {
1247                // infinite loop check
1248                if input.eof_offset() == len {
1249                    return Err(ParserError::assert(
1250                        input,
1251                        "`separated` separator parser must always consume",
1252                    ));
1253                }
1254
1255                match parser.parse_next(input) {
1256                    Err(e) if e.is_backtrack() => {
1257                        input.reset(&start);
1258                        return Ok(acc);
1259                    }
1260                    Err(e) => return Err(e),
1261                    Ok(o) => {
1262                        acc.accumulate(o);
1263                    }
1264                }
1265            }
1266        }
1267    }
1268}
1269
1270fn separated1_<I, O, C, O2, E, P, S>(
1271    parser: &mut P,
1272    separator: &mut S,
1273    input: &mut I,
1274) -> Result<C, E>
1275where
1276    I: Stream,
1277    C: Accumulate<O>,
1278    P: Parser<I, O, E>,
1279    S: Parser<I, O2, E>,
1280    E: ParserError<I>,
1281{
1282    let mut acc = C::initial(None);
1283
1284    // Parse the first element
1285    match parser.parse_next(input) {
1286        Err(e) => return Err(e),
1287        Ok(o) => {
1288            acc.accumulate(o);
1289        }
1290    }
1291
1292    loop {
1293        let start = input.checkpoint();
1294        let len = input.eof_offset();
1295        match separator.parse_next(input) {
1296            Err(e) if e.is_backtrack() => {
1297                input.reset(&start);
1298                return Ok(acc);
1299            }
1300            Err(e) => return Err(e),
1301            Ok(_) => {
1302                // infinite loop check
1303                if input.eof_offset() == len {
1304                    return Err(ParserError::assert(
1305                        input,
1306                        "`separated` separator parser must always consume",
1307                    ));
1308                }
1309
1310                match parser.parse_next(input) {
1311                    Err(e) if e.is_backtrack() => {
1312                        input.reset(&start);
1313                        return Ok(acc);
1314                    }
1315                    Err(e) => return Err(e),
1316                    Ok(o) => {
1317                        acc.accumulate(o);
1318                    }
1319                }
1320            }
1321        }
1322    }
1323}
1324
1325fn separated_n_<I, O, C, O2, E, P, S>(
1326    count: usize,
1327    parser: &mut P,
1328    separator: &mut S,
1329    input: &mut I,
1330) -> Result<C, E>
1331where
1332    I: Stream,
1333    C: Accumulate<O>,
1334    P: Parser<I, O, E>,
1335    S: Parser<I, O2, E>,
1336    E: ParserError<I>,
1337{
1338    let mut acc = C::initial(Some(count));
1339
1340    if count == 0 {
1341        return Ok(acc);
1342    }
1343
1344    let start = input.checkpoint();
1345    match parser.parse_next(input) {
1346        Err(e) => {
1347            return Err(e.append(input, &start));
1348        }
1349        Ok(o) => {
1350            acc.accumulate(o);
1351        }
1352    }
1353
1354    for _ in 1..count {
1355        let start = input.checkpoint();
1356        let len = input.eof_offset();
1357        match separator.parse_next(input) {
1358            Err(e) => {
1359                return Err(e.append(input, &start));
1360            }
1361            Ok(_) => {
1362                // infinite loop check
1363                if input.eof_offset() == len {
1364                    return Err(ParserError::assert(
1365                        input,
1366                        "`separated` separator parser must always consume",
1367                    ));
1368                }
1369
1370                match parser.parse_next(input) {
1371                    Err(e) => {
1372                        return Err(e.append(input, &start));
1373                    }
1374                    Ok(o) => {
1375                        acc.accumulate(o);
1376                    }
1377                }
1378            }
1379        }
1380    }
1381
1382    Ok(acc)
1383}
1384
1385fn separated_m_n_<I, O, C, O2, E, P, S>(
1386    min: usize,
1387    max: usize,
1388    parser: &mut P,
1389    separator: &mut S,
1390    input: &mut I,
1391) -> Result<C, E>
1392where
1393    I: Stream,
1394    C: Accumulate<O>,
1395    P: Parser<I, O, E>,
1396    S: Parser<I, O2, E>,
1397    E: ParserError<I>,
1398{
1399    if min > max {
1400        return Err(ParserError::assert(
1401            input,
1402            "range should be ascending, rather than descending",
1403        ));
1404    }
1405
1406    let mut acc = C::initial(Some(min));
1407
1408    let start = input.checkpoint();
1409    match parser.parse_next(input) {
1410        Err(e) if e.is_backtrack() => {
1411            if min == 0 {
1412                input.reset(&start);
1413                return Ok(acc);
1414            } else {
1415                return Err(e.append(input, &start));
1416            }
1417        }
1418        Err(e) => return Err(e),
1419        Ok(o) => {
1420            acc.accumulate(o);
1421        }
1422    }
1423
1424    for index in 1..max {
1425        let start = input.checkpoint();
1426        let len = input.eof_offset();
1427        match separator.parse_next(input) {
1428            Err(e) if e.is_backtrack() => {
1429                if index < min {
1430                    return Err(e.append(input, &start));
1431                } else {
1432                    input.reset(&start);
1433                    return Ok(acc);
1434                }
1435            }
1436            Err(e) => {
1437                return Err(e);
1438            }
1439            Ok(_) => {
1440                // infinite loop check
1441                if input.eof_offset() == len {
1442                    return Err(ParserError::assert(
1443                        input,
1444                        "`separated` separator parser must always consume",
1445                    ));
1446                }
1447
1448                match parser.parse_next(input) {
1449                    Err(e) if e.is_backtrack() => {
1450                        if index < min {
1451                            return Err(e.append(input, &start));
1452                        } else {
1453                            input.reset(&start);
1454                            return Ok(acc);
1455                        }
1456                    }
1457                    Err(e) => {
1458                        return Err(e);
1459                    }
1460                    Ok(o) => {
1461                        acc.accumulate(o);
1462                    }
1463                }
1464            }
1465        }
1466    }
1467
1468    Ok(acc)
1469}
1470
1471/// Alternates between two parsers, merging the results (left associative)
1472///
1473/// This stops when either parser returns [`ErrMode::Backtrack`][crate::error::ErrMode::Backtrack]. To instead chain an error up, see
1474/// [`cut_err`][crate::combinator::cut_err].
1475///
1476/// # Example
1477///
1478/// ```rust
1479/// # #[cfg(feature = "ascii")] {
1480/// # use winnow::{error::ErrMode, error::Needed};
1481/// # use winnow::prelude::*;
1482/// use winnow::combinator::separated_foldl1;
1483/// use winnow::ascii::dec_int;
1484///
1485/// fn parser(s: &mut &str) -> ModalResult<i32> {
1486///   separated_foldl1(dec_int, "-", |l, _, r| l - r).parse_next(s)
1487/// }
1488///
1489/// assert_eq!(parser.parse_peek("9-3-5"), Ok(("", 1)));
1490/// assert!(parser.parse_peek("").is_err());
1491/// assert!(parser.parse_peek("def|abc").is_err());
1492/// # }
1493/// ```
1494pub fn separated_foldl1<Input, Output, Sep, Error, ParseNext, SepParser, Op>(
1495    mut parser: ParseNext,
1496    mut sep: SepParser,
1497    mut op: Op,
1498) -> impl Parser<Input, Output, Error>
1499where
1500    Input: Stream,
1501    ParseNext: Parser<Input, Output, Error>,
1502    SepParser: Parser<Input, Sep, Error>,
1503    Error: ParserError<Input>,
1504    Op: FnMut(Output, Sep, Output) -> Output,
1505{
1506    trace("separated_foldl1", move |i: &mut Input| {
1507        let mut ol = parser.parse_next(i)?;
1508
1509        loop {
1510            let start = i.checkpoint();
1511            let len = i.eof_offset();
1512            match sep.parse_next(i) {
1513                Err(e) if e.is_backtrack() => {
1514                    i.reset(&start);
1515                    return Ok(ol);
1516                }
1517                Err(e) => return Err(e),
1518                Ok(s) => {
1519                    // infinite loop check: the parser must always consume
1520                    if i.eof_offset() == len {
1521                        return Err(ParserError::assert(
1522                            i,
1523                            "`repeat` parsers must always consume",
1524                        ));
1525                    }
1526
1527                    match parser.parse_next(i) {
1528                        Err(e) if e.is_backtrack() => {
1529                            i.reset(&start);
1530                            return Ok(ol);
1531                        }
1532                        Err(e) => return Err(e),
1533                        Ok(or) => {
1534                            ol = op(ol, s, or);
1535                        }
1536                    }
1537                }
1538            }
1539        }
1540    })
1541}
1542
1543/// Alternates between two parsers, merging the results (right associative)
1544///
1545/// This stops when either parser returns [`ErrMode::Backtrack`][crate::error::ErrMode::Backtrack]. To instead chain an error up, see
1546/// [`cut_err`][crate::combinator::cut_err].
1547///
1548/// # Example
1549///
1550/// ```rust
1551/// # #[cfg(feature = "ascii")] {
1552/// # use winnow::{error::ErrMode, error::Needed};
1553/// # use winnow::prelude::*;
1554/// use winnow::combinator::separated_foldr1;
1555/// use winnow::ascii::dec_uint;
1556///
1557/// fn parser(s: &mut &str) -> ModalResult<u32> {
1558///   separated_foldr1(dec_uint, "^", |l: u32, _, r: u32| l.pow(r)).parse_next(s)
1559/// }
1560///
1561/// assert_eq!(parser.parse_peek("2^3^2"), Ok(("", 512)));
1562/// assert_eq!(parser.parse_peek("2"), Ok(("", 2)));
1563/// assert!(parser.parse_peek("").is_err());
1564/// assert!(parser.parse_peek("def|abc").is_err());
1565/// # }
1566/// ```
1567#[cfg(feature = "alloc")]
1568pub fn separated_foldr1<Input, Output, Sep, Error, ParseNext, SepParser, Op>(
1569    mut parser: ParseNext,
1570    mut sep: SepParser,
1571    mut op: Op,
1572) -> impl Parser<Input, Output, Error>
1573where
1574    Input: Stream,
1575    ParseNext: Parser<Input, Output, Error>,
1576    SepParser: Parser<Input, Sep, Error>,
1577    Error: ParserError<Input>,
1578    Op: FnMut(Output, Sep, Output) -> Output,
1579{
1580    trace("separated_foldr1", move |i: &mut Input| {
1581        let ol = parser.parse_next(i)?;
1582        let all: alloc::vec::Vec<(Sep, Output)> =
1583            repeat(0.., (sep.by_ref(), parser.by_ref())).parse_next(i)?;
1584        if let Some((s, or)) = all
1585            .into_iter()
1586            .rev()
1587            .reduce(|(sr, or), (sl, ol)| (sl, op(ol, sr, or)))
1588        {
1589            let merged = op(ol, s, or);
1590            Ok(merged)
1591        } else {
1592            Ok(ol)
1593        }
1594    })
1595}
1596
1597/// Repeats the embedded parser, filling the given slice with results.
1598///
1599/// This parser fails if the input runs out before the given slice is full.
1600///
1601/// # Example
1602///
1603/// ```rust
1604/// # use winnow::{error::ErrMode, error::Needed};
1605/// # use winnow::prelude::*;
1606/// use winnow::combinator::fill;
1607///
1608/// fn parser<'i>(s: &mut &'i str) -> ModalResult<[&'i str; 2]> {
1609///   let mut buf = ["", ""];
1610///   fill("abc", &mut buf).parse_next(s)?;
1611///   Ok(buf)
1612/// }
1613///
1614/// assert_eq!(parser.parse_peek("abcabc"), Ok(("", ["abc", "abc"])));
1615/// assert!(parser.parse_peek("abc123").is_err());
1616/// assert!(parser.parse_peek("123123").is_err());
1617/// assert!(parser.parse_peek("").is_err());
1618/// assert_eq!(parser.parse_peek("abcabcabc"), Ok(("abc", ["abc", "abc"])));
1619/// ```
1620pub fn fill<'i, Input, Output, Error, ParseNext>(
1621    mut parser: ParseNext,
1622    buf: &'i mut [Output],
1623) -> impl Parser<Input, (), Error> + 'i
1624where
1625    Input: Stream + 'i,
1626    ParseNext: Parser<Input, Output, Error> + 'i,
1627    Error: ParserError<Input> + 'i,
1628{
1629    trace("fill", move |i: &mut Input| {
1630        for elem in buf.iter_mut() {
1631            let start = i.checkpoint();
1632            match parser.parse_next(i) {
1633                Ok(o) => {
1634                    *elem = o;
1635                }
1636                Err(e) => {
1637                    return Err(e.append(i, &start));
1638                }
1639            }
1640        }
1641
1642        Ok(())
1643    })
1644}