8 releases
0.2.1 | Apr 30, 2024 |
---|---|
0.2.0 | Apr 30, 2024 |
0.1.4 | Apr 30, 2024 |
0.0.0 | Apr 24, 2024 |
#235 in Rust patterns
3,904 downloads per month
Used in 3 crates
200KB
2.5K
SLoC
The definitive non-empty slice/array/vec library for Rust.
Features
Nonempty-by-construction API
let mut my_vec = NonEmpty::<Vec<_>>::of("hello"); // construct once
my_vec.push("world"); // continue using your normal APIs
let hello: &str = my_vec.first(); // preserve the guarantee that there is at least one element
#[repr(transparent)]
allows advanced usecases and guarantees optimum performance[^1]:
let src = &mut ["hello", "world"];
let ne = NonEmpty::<[_]>::new_mut(src).unwrap();
// ^ uses the same backing memory
let world: &str = ne.last();
Total API coverage.
For every impl of From
, TryFrom
, PartialEq
and PartialOrd
in [std
][^2],
there is a corresponding impl in this library for Slice
, Array
and [Vec
].
This includes more exotic types:
let nun: Box<NonEmpty<[_]>> = vec![0xDEAD, 0xBEEF].into();
let cow: Cow<NonEmpty<[_]>> = (&*nun).into();
let arc: Arc<NonEmpty<[_]>> = cow.into_owned().into();
const
-friendly API. Where possible, all methods are const
.
const TWO: &NonEmpty<[&str]> = slice!["together", "forever"];
const FIRST: &str = TWO.first();
const ONE: &NonEmpty<[&str]> = NonEmpty::<[_]>::of(&"lonely");
Extensive feature gating supporting:
no-std
environments with no allocator.alloc
-enabled environments.- full-
std
-enabled environments. - interaction with crates like
serde
andarbitrary
.
Iterator support:
Specialized Iterator
methods remove branches to handle empty iterators,
and preserve invariants even when chaining combinators.
let v = vec![1, 2, 3];
let _: Option<&u8> = v.iter().last();
// ^ normally you have to handle the empty case
let _: &u8 = v.iter_ne().last();
// ^ but we know there is at least one element
let _: u8 = v.iter_ne().copied().last();
// ^ using this combinator preserves the invariant
Thoughtful design:
NonZeroUsize
is inserted where appropriate.- Everything
Deref
/DerefMut
s down to aNonEmpty<Slice<T>>
, which in turnderef/mut
s down to a[T]
. - Liberal applications of
cmp
,borrow
,convert
traits. If there's a missing API that you'd like, please raise an issue!
[^1]: Other crates like nonempty
require an indirection.
[^2]: Barring impls on !#[fundamental]
types like Arc
.
Fun fact: our tests were generated from [std
]'s rustdoc!
Dependencies
~0–1MB
~18K SLoC