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
//! Traits involving the capacity of a collection.
use super::len::Len;

/// A trait for describing the capacity of a collection.
///
/// Because frequently allocating memory can be inefficient, collections often store room for more
/// data than they actually hold. This "extra length" is represented by capacity, stating the
/// maximum length that can be occupied without any memory allocations.
///
/// Obtaining the capacity of the collection must take a constant amount of time and space.
pub trait Capacity: Len {
    /// Returns the capacity of the collection.
    ///
    /// If this collection stores zero-sized types, then it effectively has infinite capacity. For
    /// this reason, those collections should have a capacity of `usize::MAX`.
    fn capacity(&self) -> usize;
}

/// A trait for creating an empty collection with a given, pre-allocated capacity.
///
/// If a user knows in advance a minimum bound for how much capacity they will need, they can use
/// the `with_capacity` trait to pre-allocate memory in advance. The resulting collection is
/// guaranteed to have at least the capacity given.
///
/// If the given capacity is zero, then no capacity should be allocated at all. The behaviour of the
/// `Default` implementation should act the same as `with_capacity(0)`.
///
/// Creating a collection with a given capacity should take linear time and space with respect to
/// the requested capacity. Creating a collection of zero-size types should always take constant
/// time and space.
pub trait WithCapacity: Capacity + Default {
    /// Creates a value of the given capacity.
    ///
    /// If a value of zero is given, this should have the same effect as calling `Default::default`,
    /// and should not allocate any memory.
    fn with_capacity(capacity: usize) -> Self;
}

/// A trait for modifying the capacity of a collection.
///
/// These methods are mostly hints to
///
/// Clearing a collection must take at most a linear amount of time and space with respect to the
/// number of elements which are dropped.
pub trait CapacityMut: WithCapacity {
    /// Ensures that the capacity is at least the current length plus `additional`.
    fn reserve(&mut self, additional: usize);

    /// Similar to `reserve`, adding a strong hint to not reserve capacity above what's needed.
    ///
    /// By default, this method just delegates to `reserve` unless the implementation has a more
    /// efficient version..
    fn reserve_exact(&mut self, additional: usize) {
        CapacityMut::reserve(self, additional)
    }

    /// Reduces the capacity down as close as possible to the current length.
    ///
    /// If the length of the collection is zero, this method will set its capacity to zero. By
    /// default, this method does nothing unless the capacity is zero.
    fn shrink_to_fit(&mut self) {
        if Len::is_empty(self) {
            *self = Default::default();
        }
    }
}