1 use crate::stream::Stream; 2 3 use core::future::Future; 4 use core::pin::Pin; 5 use core::task::{Context, Poll}; 6 use pin_project_lite::pin_project; 7 8 pin_project! { 9 /// Future returned by the [`fold`](super::StreamExt::fold) method. 10 #[derive(Debug)] 11 pub struct FoldFuture<St, B, F> { 12 #[pin] 13 stream: St, 14 acc: Option<B>, 15 f: F, 16 } 17 } 18 19 impl<St, B, F> FoldFuture<St, B, F> { new(stream: St, init: B, f: F) -> Self20 pub(super) fn new(stream: St, init: B, f: F) -> Self { 21 Self { 22 stream, 23 acc: Some(init), 24 f, 25 } 26 } 27 } 28 29 impl<St, B, F> Future for FoldFuture<St, B, F> 30 where 31 St: Stream, 32 F: FnMut(B, St::Item) -> B, 33 { 34 type Output = B; 35 poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output>36 fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> { 37 let mut me = self.project(); 38 loop { 39 let next = ready!(me.stream.as_mut().poll_next(cx)); 40 41 match next { 42 Some(v) => { 43 let old = me.acc.take().unwrap(); 44 let new = (me.f)(old, v); 45 *me.acc = Some(new); 46 } 47 None => return Poll::Ready(me.acc.take().unwrap()), 48 } 49 } 50 } 51 } 52