1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76
//! Traits for moving data between collectinos without freeing resources. cfg_if! { if #[cfg(feature = "std")] { use std::mem::swap; } else { use core::mem::swap; } } use len_trait::Clear; use base::{CanPush, Push}; use ordered::{PushBack, PushFront}; /// A trait for moving data from one collection into another without freeing resources. /// /// Conceptually, an `append` is equivalent to a [`push`], with the caveat that the data is "moved /// out" of the pushed collection instead of being consumed. This allows reuse of the pushed /// collection's resources. /// /// [`push`]: ../base/trait.Push.html#tymethod.push pub trait Append: Sized + Clear { /// Moves data out of `val` and into this collection. /// /// Invoking this method should make `val` empty without freeing any resources. Any data that /// would be pushed out of `self` should be retained in `val`. fn append(&mut self, val: &mut Self); } impl<T: Append> CanPush<T> for T { type PushedOut = T; } impl<T: Append> Push<T> for T { fn push(&mut self, mut val: T) -> Option<T> { self.append(&mut val); if val.is_empty() { None } else { Some(val) } } } /// A trait for moving data from one collection onto the back of another without freeing resources. /// /// This trait is the [`PushBack`] analogue of [`Append`]. /// /// [`PushBack`]: ../ordered/trait.PushBack.html /// [`Append`]: trait.Append.html pub trait AppendBack: Append { /// Moves data out of `val` and onto the back of this collection. /// /// Invoking this method should make `val` empty without freeing any resources. fn append_back(&mut self, val: &mut Self) { self.append(val) } } impl<T: AppendBack> PushBack<T> for T {} /// A trait for moving data from one collection onto the front of another without freeing resources. /// /// This trait is the [`PushFront`] analogue of [`Append`]. /// /// [`PushFront`]: ../ordered/trait.PushBack.html /// [`Append`]: trait.Append.html pub trait AppendFront: AppendBack { /// Moves data out of `val` and onto the front of this collection. /// /// Invoking this method should make `val` empty without freeing any resources. fn append_front(&mut self, val: &mut Self) { swap(val, self); val.append_back(self) } } impl<T: AppendFront> PushFront<T> for T { fn push_front(&mut self, mut val: T) -> Option<T> { self.append_front(&mut val); if val.is_empty() { None } else { Some(val) } } }