Struct Array

#[repr(transparent)]
pub struct Array<T, U: ArraySize>(pub U::ArrayType<T>);

Array is a newtype for an inner [T; N] array where N is determined by a generic ArraySize parameter, which is a marker trait for a numeric value determined by ZSTs that impl the typenum::Unsigned trait.

The inner [T; N] field is pub which means it's possible to write Array literals like:

Array is defined as repr(transparent), meaning it can be used anywhere an appropriately sized [T; N] type is used in unsafe code / FFI.

use hybrid_array::{Array, sizes::U3};

let arr: Array<u8, U3> = Array([1, 2, 3]);

Fields

0: U::ArrayType<T>

Implementations

impl<T> Array<T, U1>

const fn from_ref(r: &T) -> &Self

Convert a reference to T into a reference to an Array of length U1.

const fn from_mut(r: &mut T) -> &mut Self

Converts a mutable reference to T into a mutable reference to an Array of length U1.

impl<T, U> Array<MaybeUninit<T>, U> where U: ArraySize,

const fn uninit() -> Array<MaybeUninit<T>, U>

Create an uninitialized array of MaybeUninits for the given type.

unsafe fn assume_init(self) -> Array<T, U>

Extract the values from an array of MaybeUninit containers.

Safety

It is up to the caller to guarantee that all elements of the array are in an initialized state.

impl<T, U> Array<T, U> where U: ArraySize,

const fn as_slice(&self) -> &[T]

Returns a slice containing the entire array. Equivalent to &s[..].

const fn as_mut_slice(&mut self) -> &mut [T]

Returns a mutable slice containing the entire array. Equivalent to &mut s[..].

const fn as_ptr(&self) -> *const T

Returns a pointer to the start of the array.

const fn as_mut_ptr(&mut self) -> *mut T

Returns a mutable pointer to the start of the array.

fn iter(&self) -> Iter<'_, T>

Returns an iterator over the array.

fn iter_mut(&mut self) -> IterMut<'_, T>

Returns an iterator that allows modifying each value.

fn map<F, O>(self, f: F) -> Array<O, U>
where
    F: FnMut(T) -> O,

Returns an array of the same size as self, with function f applied to each element in order.

fn concat<N>(self, other: Array<T, N>) -> Array<T, Sum<U, N>>
where
    N: ArraySize,
    U: Add<N>,
    Sum<U, N>: ArraySize,

Concatenates self with other.

fn split<N>(self) -> (Array<T, N>, Array<T, Diff<U, N>>)
where
    U: Sub<N>,
    N: ArraySize,
    Diff<U, N>: ArraySize,

Splits self at index N in two arrays.

New arrays hold the original memory from self.

fn split_ref<N>(&self) -> (&'_ Array<T, N>, &'_ Array<T, Diff<U, N>>)
where
    U: Sub<N>,
    N: ArraySize,
    Diff<U, N>: ArraySize,

Splits &self at index N in two array references.

fn split_ref_mut<N>(&mut self) -> (&'_ mut Array<T, N>, &'_ mut Array<T, Diff<U, N>>)
where
    U: Sub<N>,
    N: ArraySize,
    Diff<U, N>: ArraySize,

Splits &mut self at index N in two mutable array references.

const fn slice_as_array(slice: &[T]) -> Option<&Self>

Get a reference to an array from a slice, if the slice is exactly the size of the array.

Returns None if the slice's length is not exactly equal to the array size.

const fn slice_as_mut_array(slice: &mut [T]) -> Option<&mut Self>

Get a mutable reference to an array from a slice, if the slice is exactly the size of the array.

Returns None if the slice's length is not exactly equal to the array size.

const fn slice_as_chunks(buf: &[T]) -> (&[Self], &[T])

Splits the shared slice into a slice of U-element arrays, starting at the beginning of the slice, and a remainder slice with length strictly less than U.

Panics

Panics if U is 0.

const fn slice_as_chunks_mut(buf: &mut [T]) -> (&mut [Self], &mut [T])

Splits the exclusive slice into a slice of U-element arrays, starting at the beginning of the slice, and a remainder slice with length strictly less than U.

Panics

Panics if U is 0.

const fn slice_as_flattened(slice: &[Self]) -> &[T]

Obtain a flattened slice from a slice of array chunks.

Panics

  • if the length calculation for the flattened slice overflows
const fn slice_as_flattened_mut(slice: &mut [Self]) -> &mut [T]

Obtain a mutable flattened slice from a mutable slice of array chunks.

Panics

  • if the length calculation for the flattened slice overflows

impl<T, U> Array<T, U> where U: ArraySize,

fn try_from_iter<I: IntoIterator<Item = T>>(iter: I) -> Result<Self, TryFromIteratorError>

Construct an array from the given iterator, returning TryFromIteratorError in the event that the number of items in the iterator does not match the array size.

Errors

Returns TryFromIteratorError in the event the iterator does not return a number of items which is exactly equal to the array size.

impl<T, U> Array<T, U> where U: ArraySize,

fn from_fn(f: impl FnMut(usize) -> T) -> Self

Create array where each array element T is returned by the f call.

fn try_from_fn<E>(f: impl FnMut(usize) -> Result<T, E>) -> Result<Self, E>

Create array fallibly where each array element T is returned by the f call, or return an error if any are encountered.

Errors

Propagates the E type returned from the provided F in the event of error.

impl<T, U> Array<T, U> where U: ArraySize,

fn from_slice(slice: &[T]) -> &Self

Convert the given slice into a reference to a hybrid array.

Panics

Panics if the slice's length doesn't match the array type.

fn from_mut_slice(slice: &mut [T]) -> &mut Self

Convert the given mutable slice to a mutable reference to a hybrid array.

Panics

Panics if the slice's length doesn't match the array type.

fn clone_from_slice(slice: &[T]) -> Self
where
    Self: Clone,

Clone the contents of the slice as a new hybrid array.

Panics

Panics if the slice's length doesn't match the array type.

impl<T, U, V> Array<Array<T, U>, V> where U: ArraySize, V: ArraySize,

const fn as_flattened(&self) -> &[T]

Takes a &Array<Array<T, N>, >>, and flattens it to a &[T].

Panics

This panics if the length of the resulting slice would overflow a usize.

This is only possible when flattening a slice of arrays of zero-sized types, and thus tends to be irrelevant in practice. If size_of::<T>() > 0, this will never panic.

Examples

use hybrid_array::{Array, typenum::{U0, U2, U3, U5, U10}};

let a: Array<Array<usize, U3>, U2> = Array([Array([1, 2, 3]), Array([4, 5, 6])]);
assert_eq!(a.as_flattened(), &[1, 2, 3, 4, 5, 6]);

let b: Array<Array<usize, U2>, U3> = Array([Array([1, 2]), Array([3, 4]), Array([5, 6])]);
assert_eq!(a.as_flattened(), b.as_flattened());

let c: Array<[usize; 2], U3> = Array([[1, 2], [3, 4], [5, 6]]);
assert_eq!(a.as_flattened(), c.as_flattened());

let slice_of_empty_arrays: &Array<Array<i32, U5>, U0> = &Array::from_fn(|_| Array([1, 2, 3, 4, 5]));
assert!(slice_of_empty_arrays.as_flattened().is_empty());

let empty_slice_of_arrays: &Array<Array<u32, U10>, U0>  = &Array([]);
assert!(empty_slice_of_arrays.as_flattened().is_empty());
const fn as_flattened_mut(&mut self) -> &mut [T]

Takes a &mut Array<Array<T, N>,M>, and flattens it to a &mut [T].

Panics

This panics if the length of the resulting slice would overflow a usize.

This is only possible when flattening a slice of arrays of zero-sized types, and thus tends to be irrelevant in practice. If size_of::<T>() > 0, this will never panic.

Examples

use hybrid_array::{Array, typenum::U3};

fn add_5_to_all(slice: &mut [i32]) {
    for i in slice {
        *i += 5;
    }
}

let mut array: Array<Array<i32, U3>, U3> = Array([Array([1_i32, 2, 3]), Array([4, 5, 6]), Array([7, 8, 9])]);
add_5_to_all(array.as_flattened_mut());
assert_eq!(array, Array([Array([6, 7, 8]), Array([9, 10, 11]), Array([12, 13, 14])]));

impl<T, U, const N: usize> Array<T, U> where U: ArraySize<ArrayType<T> = [T; N]>,

const fn cast_from_core(array_ref: &[T; N]) -> &Self

Cast a reference to a core array to an Array reference.

const fn cast_from_core_mut(array_ref: &mut [T; N]) -> &mut Self

Cast a mutable reference to a core array to an Array reference.

const fn cast_slice_from_core(slice: &[[T; N]]) -> &[Self]

Transform slice to slice of core array type.

const fn cast_slice_from_core_mut(slice: &mut [[T; N]]) -> &mut [Self]

Transform mutable slice to mutable slice of core array type.

const fn cast_slice_to_core(slice: &[Self]) -> &[[T; N]]

Transform slice to slice of core array type.

const fn cast_slice_to_core_mut(slice: &mut [Self]) -> &mut [[T; N]]

Transform mutable slice to mutable slice of core array type.

Trait Implementations

impl<'a, T, U> TryFrom<&'a [T]> for Array<T, U> where Self: Clone, U: ArraySize,

type Error = TryFromSliceError;
fn try_from(slice: &'a [T]) -> Result<Array<T, U>, TryFromSliceError>

impl<T, I, U> Index<I> for Array<T, U> where [T]: Index<I>, U: ArraySize,

type Output = <[T] as Index<I>>::Output;
fn index(&self, index: I) -> &Self::Output

impl<T, I, U> IndexMut<I> for Array<T, U> where [T]: IndexMut<I>, U: ArraySize,

fn index_mut(&mut self, index: I) -> &mut Self::Output

impl<T, N, M> Flatten<T, <M as Mul<N>>::Output> for Array<Array<T, M>, N> where N: ArraySize, M: ArraySize + Mul<N>, Prod<M, N>: ArraySize,

type OutputSize = <M as Mul<N>>::Output;
fn flatten(self) -> Array<T, Self::OutputSize>

impl<T, N, M> Unflatten<M> for Array<T, N> where N: ArraySize + Div<M> + Rem<M, Output = U0>, M: ArraySize, Quot<N, M>: ArraySize,

type Part = Array<T, <N as Div<M>>::Output>;
fn unflatten(self) -> Array<Self::Part, M>

impl<T, U> AsArrayMut<T> for Array<T, U> where U: ArraySize,

fn as_array_mut(&mut self) -> &mut Self

impl<T, U> AsArrayRef<T> for Array<T, U> where U: ArraySize,

fn as_array_ref(&self) -> &Self

impl<T, U> AsMut<Array<T, U>> for Array<T, U> where U: ArraySize,

fn as_mut(&mut self) -> &mut Self

impl<T, U> AsMut<[T]> for Array<T, U> where U: ArraySize,

fn as_mut(&mut self) -> &mut [T]

impl<T, U> AsRef<Array<T, U>> for Array<T, U> where U: ArraySize,

fn as_ref(&self) -> &Self

impl<T, U> AsRef<[T]> for Array<T, U> where U: ArraySize,

fn as_ref(&self) -> &[T]

impl<T, U> AssocArraySize for Array<T, U> where U: ArraySize,

type Size = U;

impl<T, U> Borrow<[T]> for Array<T, U> where U: ArraySize,

fn borrow(&self) -> &[T]

impl<T, U> BorrowMut<[T]> for Array<T, U> where U: ArraySize,

fn borrow_mut(&mut self) -> &mut [T]

impl<T, U> Clone for Array<T, U> where T: Clone, U: ArraySize,

fn clone(&self) -> Self

impl<T, U> Copy for Array<T, U> where T: Copy, U: ArraySize, U::ArrayType<T>: Copy,

impl<T, U> Debug for Array<T, U> where T: Debug, U: ArraySize,

fn fmt(&self, f: &mut Formatter<'_>) -> Result

impl<T, U> Default for Array<T, U> where T: Default, U: ArraySize,

fn default() -> Self

impl<T, U> Deref for Array<T, U> where U: ArraySize,

type Target = [T];
fn deref(&self) -> &[T]

impl<T, U> DerefMut for Array<T, U> where U: ArraySize,

fn deref_mut(&mut self) -> &mut [T]

impl<T, U> Eq for Array<T, U> where T: Eq, U: ArraySize,

impl<T, U> FromIterator<T> for Array<T, U> where U: ArraySize,

fn from_iter<I: IntoIterator<Item = T>>(iter: I) -> Self

impl<T, U> Hash for Array<T, U> where T: Hash, U: ArraySize,

fn hash<H: Hasher>(&self, state: &mut H)

impl<T, U> IntoIterator for Array<T, U> where U: ArraySize,

type Item = T;
type IntoIter = <<U as ArraySize>::ArrayType<T> as IntoIterator>::IntoIter;
fn into_iter(self) -> Self::IntoIter

Creates a consuming iterator, that is, one that moves each value out of the array (from start to end).

The array cannot be used after calling this unless T implements Copy, so the whole array is copied.

impl<T, U> Ord for Array<T, U> where T: Ord, U: ArraySize,

fn cmp(&self, other: &Self) -> Ordering

impl<T, U> PartialEq for Array<T, U> where T: PartialEq, U: ArraySize,

fn eq(&self, other: &Self) -> bool

impl<T, U> PartialOrd for Array<T, U> where T: PartialOrd, U: ArraySize,

fn partial_cmp(&self, other: &Self) -> Option<Ordering>

impl<T, U, const N: usize> AsMut<[T; N]> for Array<T, U> where U: ArraySize<ArrayType<T> = [T; N]>,

fn as_mut(&mut self) -> &mut [T; N]

impl<T, U, const N: usize> AsRef<[T; N]> for Array<T, U> where U: ArraySize<ArrayType<T> = [T; N]>,

fn as_ref(&self) -> &[T; N]

impl<T, U, const N: usize> Borrow<[T; N]> for Array<T, U> where U: ArraySize<ArrayType<T> = [T; N]>,

fn borrow(&self) -> &[T; N]

impl<T, U, const N: usize> BorrowMut<[T; N]> for Array<T, U> where U: ArraySize<ArrayType<T> = [T; N]>,

fn borrow_mut(&mut self) -> &mut [T; N]

impl<T, U, const N: usize> From<[T; N]> for Array<T, U> where U: ArraySize<ArrayType<T> = [T; N]>,

fn from(arr: [T; N]) -> Array<T, U>

impl<T, U, const N: usize> PartialEq<[T; N]> for Array<T, U> where T: PartialEq, U: ArraySize<ArrayType<T> = [T; N]>,

fn eq(&self, other: &[T; N]) -> bool

impl<T, U: ArraySize> Send for Array<T, U> where T: Send,

impl<T, U: ArraySize> Sync for Array<T, U> where T: Sync,

Auto Trait Implementations

impl<T, U> Freeze for Array<T, U> where <U as ArraySize>::ArrayType<T>: Freeze,

impl<T, U> RefUnwindSafe for Array<T, U> where <U as ArraySize>::ArrayType<T>: RefUnwindSafe,

impl<T, U> Unpin for Array<T, U> where <U as ArraySize>::ArrayType<T>: Unpin,

impl<T, U> UnsafeUnpin for Array<T, U> where <U as ArraySize>::ArrayType<T>: UnsafeUnpin,

impl<T, U> UnwindSafe for Array<T, U> where <U as ArraySize>::ArrayType<T>: UnwindSafe,

Blanket Implementations

impl<P, T> Receiver for Array<T, U> where P: Deref<Target = T> + ?Sized, T: ?Sized,

type Target = T;

impl<T> Any for Array<T, U> where T: 'static + ?Sized,

fn type_id(&self) -> TypeId

impl<T> Borrow<T> for Array<T, U> where T: ?Sized,

fn borrow(&self) -> &T

impl<T> BorrowMut<T> for Array<T, U> where T: ?Sized,

fn borrow_mut(&mut self) -> &mut T

impl<T> CloneToUninit for Array<T, U> where T: Clone,

unsafe fn clone_to_uninit(&self, dest: *mut u8)

impl<T> From<T> for Array<T, U>

fn from(t: T) -> T

Returns the argument unchanged.

impl<T> Same for Array<T, U>

type Output = T;

impl<T, U> Into<U> for Array<T, U> where U: From<T>,

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of [From]<T> for U chooses to do.

impl<T, U> TryFrom<U> for Array<T, U> where U: Into<T>,

type Error = never;
fn try_from(value: U) -> Result<T, never>

impl<T, U> TryInto<U> for Array<T, U> where U: TryFrom<T>,

type Error = <U as TryFrom<T>>::Error;
fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>