futures_lite/
future.rs

1//! Combinators for the [`Future`] trait.
2//!
3//! # Examples
4//!
5//! ```
6//! use futures_lite::future;
7//!
8//! # spin_on::spin_on(async {
9//! for step in 0..3 {
10//!     println!("step {}", step);
11//!
12//!     // Give other tasks a chance to run.
13//!     future::yield_now().await;
14//! }
15//! # });
16//! ```
17
18#[cfg(all(not(feature = "std"), feature = "alloc"))]
19extern crate alloc;
20
21#[doc(no_inline)]
22pub use core::future::{pending, ready, Future, Pending, Ready};
23
24use core::fmt;
25use core::pin::Pin;
26
27use pin_project_lite::pin_project;
28
29#[cfg(feature = "std")]
30use std::{
31    any::Any,
32    panic::{catch_unwind, AssertUnwindSafe, UnwindSafe},
33};
34
35#[cfg(feature = "race")]
36use fastrand::Rng;
37
38#[cfg(all(not(feature = "std"), feature = "alloc"))]
39use alloc::boxed::Box;
40use core::task::{Context, Poll};
41
42/// Blocks the current thread on a future.
43///
44/// # Examples
45///
46/// ```
47/// use futures_lite::future;
48///
49/// let val = future::block_on(async {
50///     1 + 2
51/// });
52///
53/// assert_eq!(val, 3);
54/// ```
55#[cfg(feature = "std")]
56pub fn block_on<T>(future: impl Future<Output = T>) -> T {
57    use core::cell::RefCell;
58    use core::task::Waker;
59
60    use parking::Parker;
61
62    // Pin the future on the stack.
63    crate::pin!(future);
64
65    // Creates a parker and an associated waker that unparks it.
66    fn parker_and_waker() -> (Parker, Waker) {
67        let parker = Parker::new();
68        let unparker = parker.unparker();
69        let waker = Waker::from(unparker);
70        (parker, waker)
71    }
72
73    thread_local! {
74        // Cached parker and waker for efficiency.
75        static CACHE: RefCell<(Parker, Waker)> = RefCell::new(parker_and_waker());
76    }
77
78    CACHE.with(|cache| {
79        // Try grabbing the cached parker and waker.
80        let tmp_cached;
81        let tmp_fresh;
82        let (parker, waker) = match cache.try_borrow_mut() {
83            Ok(cache) => {
84                // Use the cached parker and waker.
85                tmp_cached = cache;
86                &*tmp_cached
87            }
88            Err(_) => {
89                // Looks like this is a recursive `block_on()` call.
90                // Create a fresh parker and waker.
91                tmp_fresh = parker_and_waker();
92                &tmp_fresh
93            }
94        };
95
96        let cx = &mut Context::from_waker(waker);
97        // Keep polling until the future is ready.
98        loop {
99            match future.as_mut().poll(cx) {
100                Poll::Ready(output) => return output,
101                Poll::Pending => parker.park(),
102            }
103        }
104    })
105}
106
107/// Polls a future just once and returns an [`Option`] with the result.
108///
109/// # Examples
110///
111/// ```
112/// use futures_lite::future;
113///
114/// # spin_on::spin_on(async {
115/// assert_eq!(future::poll_once(future::pending::<()>()).await, None);
116/// assert_eq!(future::poll_once(future::ready(42)).await, Some(42));
117/// # })
118/// ```
119pub fn poll_once<T, F>(f: F) -> PollOnce<F>
120where
121    F: Future<Output = T>,
122{
123    PollOnce { f }
124}
125
126pin_project! {
127    /// Future for the [`poll_once()`] function.
128    #[must_use = "futures do nothing unless you `.await` or poll them"]
129    pub struct PollOnce<F> {
130        #[pin]
131        f: F,
132    }
133}
134
135impl<F> fmt::Debug for PollOnce<F> {
136    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
137        f.debug_struct("PollOnce").finish()
138    }
139}
140
141impl<T, F> Future for PollOnce<F>
142where
143    F: Future<Output = T>,
144{
145    type Output = Option<T>;
146
147    fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
148        match self.project().f.poll(cx) {
149            Poll::Ready(t) => Poll::Ready(Some(t)),
150            Poll::Pending => Poll::Ready(None),
151        }
152    }
153}
154
155/// Creates a future from a function returning [`Poll`].
156///
157/// # Examples
158///
159/// ```
160/// use futures_lite::future;
161/// use std::task::{Context, Poll};
162///
163/// # spin_on::spin_on(async {
164/// fn f(_: &mut Context<'_>) -> Poll<i32> {
165///     Poll::Ready(7)
166/// }
167///
168/// assert_eq!(future::poll_fn(f).await, 7);
169/// # })
170/// ```
171pub fn poll_fn<T, F>(f: F) -> PollFn<F>
172where
173    F: FnMut(&mut Context<'_>) -> Poll<T>,
174{
175    PollFn { f }
176}
177
178pin_project! {
179    /// Future for the [`poll_fn()`] function.
180    #[must_use = "futures do nothing unless you `.await` or poll them"]
181    pub struct PollFn<F> {
182        f: F,
183    }
184}
185
186impl<F> fmt::Debug for PollFn<F> {
187    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
188        f.debug_struct("PollFn").finish()
189    }
190}
191
192impl<T, F> Future for PollFn<F>
193where
194    F: FnMut(&mut Context<'_>) -> Poll<T>,
195{
196    type Output = T;
197
198    fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<T> {
199        let this = self.project();
200        (this.f)(cx)
201    }
202}
203
204/// Wakes the current task and returns [`Poll::Pending`] once.
205///
206/// This function is useful when we want to cooperatively give time to the task scheduler. It is
207/// generally a good idea to yield inside loops because that way we make sure long-running tasks
208/// don't prevent other tasks from running.
209///
210/// # Examples
211///
212/// ```
213/// use futures_lite::future;
214///
215/// # spin_on::spin_on(async {
216/// future::yield_now().await;
217/// # })
218/// ```
219pub fn yield_now() -> YieldNow {
220    YieldNow(false)
221}
222
223/// Future for the [`yield_now()`] function.
224#[derive(Debug)]
225#[must_use = "futures do nothing unless you `.await` or poll them"]
226pub struct YieldNow(bool);
227
228impl Future for YieldNow {
229    type Output = ();
230
231    fn poll(mut self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
232        if !self.0 {
233            self.0 = true;
234            cx.waker().wake_by_ref();
235            Poll::Pending
236        } else {
237            Poll::Ready(())
238        }
239    }
240}
241
242/// Joins two futures, waiting for both to complete.
243///
244/// # Examples
245///
246/// ```
247/// use futures_lite::future;
248///
249/// # spin_on::spin_on(async {
250/// let a = async { 1 };
251/// let b = async { 2 };
252///
253/// assert_eq!(future::zip(a, b).await, (1, 2));
254/// # })
255/// ```
256pub fn zip<F1, F2>(future1: F1, future2: F2) -> Zip<F1, F2>
257where
258    F1: Future,
259    F2: Future,
260{
261    Zip {
262        future1: Some(future1),
263        future2: Some(future2),
264        output1: None,
265        output2: None,
266    }
267}
268
269pin_project! {
270    /// Future for the [`zip()`] function.
271    #[derive(Debug)]
272    #[must_use = "futures do nothing unless you `.await` or poll them"]
273    pub struct Zip<F1, F2>
274    where
275        F1: Future,
276        F2: Future,
277    {
278        #[pin]
279        future1: Option<F1>,
280        output1: Option<F1::Output>,
281        #[pin]
282        future2: Option<F2>,
283        output2: Option<F2::Output>,
284    }
285}
286
287/// Extracts the contents of two options and zips them, handling `(Some(_), None)` cases
288fn take_zip_from_parts<T1, T2>(o1: &mut Option<T1>, o2: &mut Option<T2>) -> Poll<(T1, T2)> {
289    match (o1.take(), o2.take()) {
290        (Some(t1), Some(t2)) => Poll::Ready((t1, t2)),
291        (o1x, o2x) => {
292            *o1 = o1x;
293            *o2 = o2x;
294            Poll::Pending
295        }
296    }
297}
298
299impl<F1, F2> Future for Zip<F1, F2>
300where
301    F1: Future,
302    F2: Future,
303{
304    type Output = (F1::Output, F2::Output);
305
306    fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
307        let mut this = self.project();
308
309        if let Some(future) = this.future1.as_mut().as_pin_mut() {
310            if let Poll::Ready(out) = future.poll(cx) {
311                *this.output1 = Some(out);
312                this.future1.set(None);
313            }
314        }
315
316        if let Some(future) = this.future2.as_mut().as_pin_mut() {
317            if let Poll::Ready(out) = future.poll(cx) {
318                *this.output2 = Some(out);
319                this.future2.set(None);
320            }
321        }
322
323        take_zip_from_parts(this.output1, this.output2)
324    }
325}
326
327/// Joins two fallible futures, waiting for both to complete or one of them to error.
328///
329/// # Examples
330///
331/// ```
332/// use futures_lite::future;
333///
334/// # spin_on::spin_on(async {
335/// let a = async { Ok::<i32, i32>(1) };
336/// let b = async { Err::<i32, i32>(2) };
337///
338/// assert_eq!(future::try_zip(a, b).await, Err(2));
339/// # })
340/// ```
341pub fn try_zip<T1, T2, E, F1, F2>(future1: F1, future2: F2) -> TryZip<F1, T1, F2, T2>
342where
343    F1: Future<Output = Result<T1, E>>,
344    F2: Future<Output = Result<T2, E>>,
345{
346    TryZip {
347        future1: Some(future1),
348        future2: Some(future2),
349        output1: None,
350        output2: None,
351    }
352}
353
354pin_project! {
355    /// Future for the [`try_zip()`] function.
356    #[derive(Debug)]
357    #[must_use = "futures do nothing unless you `.await` or poll them"]
358    pub struct TryZip<F1, T1, F2, T2> {
359        #[pin]
360        future1: Option<F1>,
361        output1: Option<T1>,
362        #[pin]
363        future2: Option<F2>,
364        output2: Option<T2>,
365    }
366}
367
368impl<T1, T2, E, F1, F2> Future for TryZip<F1, T1, F2, T2>
369where
370    F1: Future<Output = Result<T1, E>>,
371    F2: Future<Output = Result<T2, E>>,
372{
373    type Output = Result<(T1, T2), E>;
374
375    fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
376        let mut this = self.project();
377
378        if let Some(future) = this.future1.as_mut().as_pin_mut() {
379            if let Poll::Ready(out) = future.poll(cx) {
380                match out {
381                    Ok(t) => {
382                        *this.output1 = Some(t);
383                        this.future1.set(None);
384                    }
385                    Err(err) => return Poll::Ready(Err(err)),
386                }
387            }
388        }
389
390        if let Some(future) = this.future2.as_mut().as_pin_mut() {
391            if let Poll::Ready(out) = future.poll(cx) {
392                match out {
393                    Ok(t) => {
394                        *this.output2 = Some(t);
395                        this.future2.set(None);
396                    }
397                    Err(err) => return Poll::Ready(Err(err)),
398                }
399            }
400        }
401
402        take_zip_from_parts(this.output1, this.output2).map(Ok)
403    }
404}
405
406/// Returns the result of the future that completes first, preferring `future1` if both are ready.
407///
408/// If you need to treat the two futures fairly without a preference for either, use the [`race()`]
409/// function or the [`FutureExt::race()`] method.
410///
411/// # Examples
412///
413/// ```
414/// use futures_lite::future::{self, pending, ready};
415///
416/// # spin_on::spin_on(async {
417/// assert_eq!(future::or(ready(1), pending()).await, 1);
418/// assert_eq!(future::or(pending(), ready(2)).await, 2);
419///
420/// // The first future wins.
421/// assert_eq!(future::or(ready(1), ready(2)).await, 1);
422/// # })
423/// ```
424pub fn or<T, F1, F2>(future1: F1, future2: F2) -> Or<F1, F2>
425where
426    F1: Future<Output = T>,
427    F2: Future<Output = T>,
428{
429    Or { future1, future2 }
430}
431
432pin_project! {
433    /// Future for the [`or()`] function and the [`FutureExt::or()`] method.
434    #[derive(Debug)]
435    #[must_use = "futures do nothing unless you `.await` or poll them"]
436    pub struct Or<F1, F2> {
437        #[pin]
438        future1: F1,
439        #[pin]
440        future2: F2,
441    }
442}
443
444impl<T, F1, F2> Future for Or<F1, F2>
445where
446    F1: Future<Output = T>,
447    F2: Future<Output = T>,
448{
449    type Output = T;
450
451    fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
452        let this = self.project();
453
454        if let Poll::Ready(t) = this.future1.poll(cx) {
455            return Poll::Ready(t);
456        }
457        if let Poll::Ready(t) = this.future2.poll(cx) {
458            return Poll::Ready(t);
459        }
460        Poll::Pending
461    }
462}
463
464/// Fuse a future such that `poll` will never again be called once it has
465/// completed. This method can be used to turn any `Future` into a
466/// `FusedFuture`.
467///
468/// Normally, once a future has returned `Poll::Ready` from `poll`,
469/// any further calls could exhibit bad behavior such as blocking
470/// forever, panicking, never returning, etc. If it is known that `poll`
471/// may be called too often then this method can be used to ensure that it
472/// has defined semantics.
473///
474/// If a `fuse`d future is `poll`ed after having returned `Poll::Ready`
475/// previously, it will return `Poll::Pending`, from `poll` again (and will
476/// continue to do so for all future calls to `poll`).
477///
478/// This combinator will drop the underlying future as soon as it has been
479/// completed to ensure resources are reclaimed as soon as possible.
480pub fn fuse<F>(future: F) -> Fuse<F>
481where
482    F: Future + Sized,
483{
484    Fuse::new(future)
485}
486
487pin_project! {
488    /// [`Future`] for the [`fuse`] method.
489    #[derive(Debug)]
490    #[must_use = "futures do nothing unless you `.await` or poll them"]
491    pub struct Fuse<Fut> {
492        #[pin]
493        inner: Option<Fut>,
494    }
495}
496
497impl<Fut> Fuse<Fut> {
498    fn new(f: Fut) -> Self {
499        Self { inner: Some(f) }
500    }
501}
502
503impl<Fut: Future> Future for Fuse<Fut> {
504    type Output = Fut::Output;
505
506    fn poll(mut self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Fut::Output> {
507        match self
508            .as_mut()
509            .project()
510            .inner
511            .as_pin_mut()
512            .map(|f| f.poll(cx))
513        {
514            Some(Poll::Ready(output)) => {
515                self.project().inner.set(None);
516                Poll::Ready(output)
517            }
518
519            Some(Poll::Pending) | None => Poll::Pending,
520        }
521    }
522}
523
524/// Returns the result of the future that completes first, with no preference if both are ready.
525///
526/// Each time [`Race`] is polled, the two inner futures are polled in random order. Therefore, no
527/// future takes precedence over the other if both can complete at the same time.
528///
529/// If you have preference for one of the futures, use the [`or()`] function or the
530/// [`FutureExt::or()`] method.
531///
532/// # Examples
533///
534/// ```
535/// use futures_lite::future::{self, pending, ready};
536///
537/// # spin_on::spin_on(async {
538/// assert_eq!(future::race(ready(1), pending()).await, 1);
539/// assert_eq!(future::race(pending(), ready(2)).await, 2);
540///
541/// // One of the two futures is randomly chosen as the winner.
542/// let res = future::race(ready(1), ready(2)).await;
543/// # })
544/// ```
545#[cfg(all(feature = "race", feature = "std"))]
546pub fn race<T, F1, F2>(future1: F1, future2: F2) -> Race<F1, F2>
547where
548    F1: Future<Output = T>,
549    F2: Future<Output = T>,
550{
551    Race {
552        future1,
553        future2,
554        rng: Rng::new(),
555    }
556}
557
558/// Race two futures but with a predefined random seed.
559///
560/// This function is identical to [`race`], but instead of using a random seed from a thread-local
561/// RNG, it allows the user to provide a seed. It is useful for when you already have a source of
562/// randomness available, or if you want to use a fixed seed.
563///
564/// See documentation of the [`race`] function for features and caveats.
565///
566/// # Examples
567///
568/// ```
569/// use futures_lite::future::{self, pending, ready};
570///
571/// // A fixed seed is used, so the result is deterministic.
572/// const SEED: u64 = 0x42;
573///
574/// # spin_on::spin_on(async {
575/// assert_eq!(future::race_with_seed(ready(1), pending(), SEED).await, 1);
576/// assert_eq!(future::race_with_seed(pending(), ready(2), SEED).await, 2);
577///
578/// // One of the two futures is randomly chosen as the winner.
579/// let res = future::race_with_seed(ready(1), ready(2), SEED).await;
580/// # })
581/// ```
582#[cfg(feature = "race")]
583pub fn race_with_seed<T, F1, F2>(future1: F1, future2: F2, seed: u64) -> Race<F1, F2>
584where
585    F1: Future<Output = T>,
586    F2: Future<Output = T>,
587{
588    Race {
589        future1,
590        future2,
591        rng: Rng::with_seed(seed),
592    }
593}
594
595#[cfg(feature = "race")]
596pin_project! {
597    /// Future for the [`race()`] function and the [`FutureExt::race()`] method.
598    #[derive(Debug)]
599    #[must_use = "futures do nothing unless you `.await` or poll them"]
600    pub struct Race<F1, F2> {
601        #[pin]
602        future1: F1,
603        #[pin]
604        future2: F2,
605        rng: Rng,
606    }
607}
608
609#[cfg(feature = "race")]
610impl<T, F1, F2> Future for Race<F1, F2>
611where
612    F1: Future<Output = T>,
613    F2: Future<Output = T>,
614{
615    type Output = T;
616
617    fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
618        let this = self.project();
619
620        if this.rng.bool() {
621            if let Poll::Ready(t) = this.future1.poll(cx) {
622                return Poll::Ready(t);
623            }
624            if let Poll::Ready(t) = this.future2.poll(cx) {
625                return Poll::Ready(t);
626            }
627        } else {
628            if let Poll::Ready(t) = this.future2.poll(cx) {
629                return Poll::Ready(t);
630            }
631            if let Poll::Ready(t) = this.future1.poll(cx) {
632                return Poll::Ready(t);
633            }
634        }
635        Poll::Pending
636    }
637}
638
639#[cfg(feature = "std")]
640pin_project! {
641    /// Future for the [`FutureExt::catch_unwind()`] method.
642    #[derive(Debug)]
643    #[must_use = "futures do nothing unless you `.await` or poll them"]
644    pub struct CatchUnwind<F> {
645        #[pin]
646        inner: F,
647    }
648}
649
650#[cfg(feature = "std")]
651impl<F: Future + UnwindSafe> Future for CatchUnwind<F> {
652    type Output = Result<F::Output, Box<dyn Any + Send>>;
653
654    fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
655        let this = self.project();
656        catch_unwind(AssertUnwindSafe(|| this.inner.poll(cx)))?.map(Ok)
657    }
658}
659
660/// Type alias for `Pin<Box<dyn Future<Output = T> + Send + 'static>>`.
661///
662/// # Examples
663///
664/// ```
665/// use futures_lite::future::{self, FutureExt};
666///
667/// // These two lines are equivalent:
668/// let f1: future::Boxed<i32> = async { 1 + 2 }.boxed();
669/// let f2: future::Boxed<i32> = Box::pin(async { 1 + 2 });
670/// ```
671#[cfg(feature = "alloc")]
672pub type Boxed<T> = Pin<Box<dyn Future<Output = T> + Send + 'static>>;
673
674/// Type alias for `Pin<Box<dyn Future<Output = T> + 'static>>`.
675///
676/// # Examples
677///
678/// ```
679/// use futures_lite::future::{self, FutureExt};
680///
681/// // These two lines are equivalent:
682/// let f1: future::BoxedLocal<i32> = async { 1 + 2 }.boxed_local();
683/// let f2: future::BoxedLocal<i32> = Box::pin(async { 1 + 2 });
684/// ```
685#[cfg(feature = "alloc")]
686pub type BoxedLocal<T> = Pin<Box<dyn Future<Output = T> + 'static>>;
687
688/// Extension trait for [`Future`].
689pub trait FutureExt: Future {
690    /// A convenience for calling [`Future::poll()`] on `!`[`Unpin`] types.
691    fn poll(&mut self, cx: &mut Context<'_>) -> Poll<Self::Output>
692    where
693        Self: Unpin,
694    {
695        Future::poll(Pin::new(self), cx)
696    }
697
698    /// Returns the result of `self` or `other` future, preferring `self` if both are ready.
699    ///
700    /// If you need to treat the two futures fairly without a preference for either, use the
701    /// [`race()`] function or the [`FutureExt::race()`] method.
702    ///
703    /// # Examples
704    ///
705    /// ```
706    /// use futures_lite::future::{pending, ready, FutureExt};
707    ///
708    /// # spin_on::spin_on(async {
709    /// assert_eq!(ready(1).or(pending()).await, 1);
710    /// assert_eq!(pending().or(ready(2)).await, 2);
711    ///
712    /// // The first future wins.
713    /// assert_eq!(ready(1).or(ready(2)).await, 1);
714    /// # })
715    /// ```
716    fn or<F>(self, other: F) -> Or<Self, F>
717    where
718        Self: Sized,
719        F: Future<Output = Self::Output>,
720    {
721        Or {
722            future1: self,
723            future2: other,
724        }
725    }
726
727    /// Returns the result of `self` or `other` future, with no preference if both are ready.
728    ///
729    /// Each time [`Race`] is polled, the two inner futures are polled in random order. Therefore,
730    /// no future takes precedence over the other if both can complete at the same time.
731    ///
732    /// If you have preference for one of the futures, use the [`or()`] function or the
733    /// [`FutureExt::or()`] method.
734    ///
735    /// # Examples
736    ///
737    /// ```
738    /// use futures_lite::future::{pending, ready, FutureExt};
739    ///
740    /// # spin_on::spin_on(async {
741    /// assert_eq!(ready(1).race(pending()).await, 1);
742    /// assert_eq!(pending().race(ready(2)).await, 2);
743    ///
744    /// // One of the two futures is randomly chosen as the winner.
745    /// let res = ready(1).race(ready(2)).await;
746    /// # })
747    /// ```
748    #[cfg(all(feature = "std", feature = "race"))]
749    fn race<F>(self, other: F) -> Race<Self, F>
750    where
751        Self: Sized,
752        F: Future<Output = Self::Output>,
753    {
754        Race {
755            future1: self,
756            future2: other,
757            rng: Rng::new(),
758        }
759    }
760
761    /// Catches panics while polling the future.
762    ///
763    /// # Examples
764    ///
765    /// ```
766    /// use futures_lite::future::FutureExt;
767    ///
768    /// # spin_on::spin_on(async {
769    /// let fut1 = async {}.catch_unwind();
770    /// let fut2 = async { panic!() }.catch_unwind();
771    ///
772    /// assert!(fut1.await.is_ok());
773    /// assert!(fut2.await.is_err());
774    /// # })
775    /// ```
776    #[cfg(feature = "std")]
777    fn catch_unwind(self) -> CatchUnwind<Self>
778    where
779        Self: Sized + UnwindSafe,
780    {
781        CatchUnwind { inner: self }
782    }
783
784    /// Boxes the future and changes its type to `dyn Future + Send + 'a`.
785    ///
786    /// # Examples
787    ///
788    /// ```
789    /// use futures_lite::future::{self, FutureExt};
790    ///
791    /// # spin_on::spin_on(async {
792    /// let a = future::ready('a');
793    /// let b = future::pending();
794    ///
795    /// // Futures of different types can be stored in
796    /// // the same collection when they are boxed:
797    /// let futures = vec![a.boxed(), b.boxed()];
798    /// # })
799    /// ```
800    #[cfg(feature = "alloc")]
801    fn boxed<'a>(self) -> Pin<Box<dyn Future<Output = Self::Output> + Send + 'a>>
802    where
803        Self: Sized + Send + 'a,
804    {
805        Box::pin(self)
806    }
807
808    /// Boxes the future and changes its type to `dyn Future + 'a`.
809    ///
810    /// # Examples
811    ///
812    /// ```
813    /// use futures_lite::future::{self, FutureExt};
814    ///
815    /// # spin_on::spin_on(async {
816    /// let a = future::ready('a');
817    /// let b = future::pending();
818    ///
819    /// // Futures of different types can be stored in
820    /// // the same collection when they are boxed:
821    /// let futures = vec![a.boxed_local(), b.boxed_local()];
822    /// # })
823    /// ```
824    #[cfg(feature = "alloc")]
825    fn boxed_local<'a>(self) -> Pin<Box<dyn Future<Output = Self::Output> + 'a>>
826    where
827        Self: Sized + 'a,
828    {
829        Box::pin(self)
830    }
831}
832
833impl<F: Future + ?Sized> FutureExt for F {}