Skip to content

Commit cdc6acd

Browse files
authored
hybrid-array: add slice cast methods to ArrayOps (#1038)
1 parent 4766588 commit cdc6acd

File tree

3 files changed

+80
-8
lines changed

3 files changed

+80
-8
lines changed

Cargo.lock

+8-8
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

hybrid-array/src/lib.rs

+48
Original file line numberDiff line numberDiff line change
@@ -291,6 +291,7 @@ where
291291
T: Clone,
292292
U: ArraySize,
293293
{
294+
#[inline]
294295
fn clone(&self) -> Self {
295296
Self::from_fn(|n| self.0.as_ref()[n].clone())
296297
}
@@ -319,6 +320,7 @@ where
319320
T: Default,
320321
U: ArraySize,
321322
{
323+
#[inline]
322324
fn default() -> Self {
323325
Self::from_fn(|_| Default::default())
324326
}
@@ -464,6 +466,7 @@ where
464466
/// Creates a consuming iterator, that is, one that moves each value out of
465467
/// the array (from start to end). The array cannot be used after calling
466468
/// this unless `T` implements `Copy`, so the whole array is copied.
469+
#[inline]
467470
fn into_iter(self) -> Self::IntoIter {
468471
self.0.into_iter()
469472
}
@@ -476,6 +479,7 @@ where
476479
type Item = &'a T;
477480
type IntoIter = Iter<'a, T>;
478481

482+
#[inline]
479483
fn into_iter(self) -> Iter<'a, T> {
480484
self.iter()
481485
}
@@ -499,6 +503,7 @@ where
499503
T: PartialEq,
500504
U: ArraySize,
501505
{
506+
#[inline]
502507
fn eq(&self, other: &Self) -> bool {
503508
self.0.as_ref().eq(other.0.as_ref())
504509
}
@@ -509,6 +514,7 @@ where
509514
T: PartialEq,
510515
U: ArraySize<ArrayType<T> = [T; N]>,
511516
{
517+
#[inline]
512518
fn eq(&self, other: &[T; N]) -> bool {
513519
self.0.eq(other)
514520
}
@@ -519,6 +525,7 @@ where
519525
T: PartialEq,
520526
U: ArraySize<ArrayType<T> = [T; N]>,
521527
{
528+
#[inline]
522529
fn eq(&self, other: &Array<T, U>) -> bool {
523530
self.eq(&other.0)
524531
}
@@ -529,6 +536,7 @@ where
529536
T: PartialOrd,
530537
U: ArraySize,
531538
{
539+
#[inline]
532540
fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
533541
self.0.as_ref().partial_cmp(other.0.as_ref())
534542
}
@@ -539,6 +547,7 @@ where
539547
T: Ord,
540548
U: ArraySize,
541549
{
550+
#[inline]
542551
fn cmp(&self, other: &Self) -> Ordering {
543552
self.0.as_ref().cmp(other.0.as_ref())
544553
}
@@ -595,6 +604,7 @@ where
595604
T: Zeroize,
596605
U: ArraySize,
597606
{
607+
#[inline]
598608
fn zeroize(&mut self) {
599609
self.0.as_mut().iter_mut().zeroize()
600610
}
@@ -660,6 +670,18 @@ pub trait ArrayOps<T, const N: usize>:
660670
fn map_to_core_array<F, U>(self, f: F) -> [U; N]
661671
where
662672
F: FnMut(T) -> U;
673+
674+
/// Transform slice to slice of core array type
675+
fn cast_slice_to_core(slice: &[Self]) -> &[[T; N]];
676+
677+
/// Transform mutable slice to mutable slice of core array type
678+
fn cast_slice_to_core_mut(slice: &mut [Self]) -> &mut [[T; N]];
679+
680+
/// Transform slice to slice of core array type
681+
fn cast_slice_from_core(slice: &[[T; N]]) -> &[Self];
682+
683+
/// Transform mutable slice to mutable slice of core array type
684+
fn cast_slice_from_core_mut(slice: &mut [[T; N]]) -> &mut [Self];
663685
}
664686

665687
impl<T, const N: usize> ArrayOps<T, N> for [T; N] {
@@ -697,6 +719,26 @@ impl<T, const N: usize> ArrayOps<T, N> for [T; N] {
697719
{
698720
self.map(f)
699721
}
722+
723+
#[inline]
724+
fn cast_slice_to_core(slice: &[Self]) -> &[[T; N]] {
725+
slice
726+
}
727+
728+
#[inline]
729+
fn cast_slice_to_core_mut(slice: &mut [Self]) -> &mut [[T; N]] {
730+
slice
731+
}
732+
733+
#[inline]
734+
fn cast_slice_from_core(slice: &[[T; N]]) -> &[Self] {
735+
slice
736+
}
737+
738+
#[inline]
739+
fn cast_slice_from_core_mut(slice: &mut [[T; N]]) -> &mut [Self] {
740+
slice
741+
}
700742
}
701743

702744
/// Slice operations which don't have access to a const generic array size.
@@ -713,13 +755,15 @@ pub trait SliceOps<T>:
713755
/// Splits the shared slice into a slice of `N`-element arrays.
714756
///
715757
/// See [`slice_as_chunks`] for more information.
758+
#[inline]
716759
fn as_array_chunks<N: ArraySize>(&self) -> (&[Array<T, N>], &[T]) {
717760
slice_as_chunks(self.as_ref())
718761
}
719762

720763
/// Splits the exclusive slice into a slice of `N`-element arrays.
721764
///
722765
/// See [`slice_as_chunks_mut`] for more information.
766+
#[inline]
723767
fn as_array_chunks_mut<N: ArraySize>(&mut self) -> (&mut [Array<T, N>], &mut [T]) {
724768
slice_as_chunks_mut(self.as_mut())
725769
}
@@ -774,6 +818,7 @@ impl<T, U> FromFn<T> for Array<T, U>
774818
where
775819
U: ArraySize,
776820
{
821+
#[inline]
777822
fn from_fn<F>(cb: F) -> Self
778823
where
779824
F: FnMut(usize) -> T,
@@ -783,6 +828,7 @@ where
783828
}
784829

785830
impl<T, const N: usize> FromFn<T> for [T; N] {
831+
#[inline]
786832
fn from_fn<F>(cb: F) -> Self
787833
where
788834
F: FnMut(usize) -> T,
@@ -797,6 +843,7 @@ impl<T, const N: usize> FromFn<T> for [T; N] {
797843
/// # Panics
798844
/// Panics if `N` is 0.
799845
#[allow(clippy::arithmetic_side_effects)]
846+
#[inline]
800847
pub fn slice_as_chunks<T, N: ArraySize>(buf: &[T]) -> (&[Array<T, N>], &[T]) {
801848
assert_ne!(N::USIZE, 0, "chunk size must be non-zero");
802849
// Arithmetic safety: we have checked that `N::USIZE` is not zero, thus
@@ -819,6 +866,7 @@ pub fn slice_as_chunks<T, N: ArraySize>(buf: &[T]) -> (&[Array<T, N>], &[T]) {
819866
/// # Panics
820867
/// Panics if `N` is 0.
821868
#[allow(clippy::arithmetic_side_effects)]
869+
#[inline]
822870
pub fn slice_as_chunks_mut<T, N: ArraySize>(buf: &mut [T]) -> (&mut [Array<T, N>], &mut [T]) {
823871
assert_ne!(N::USIZE, 0, "chunk size must be non-zero");
824872
// Arithmetic safety: we have checked that `N::USIZE` is not zero, thus

hybrid-array/src/sizes.rs

+24
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,30 @@ macro_rules! impl_array_size {
5050
{
5151
self.0.map(f)
5252
}
53+
54+
#[inline]
55+
fn cast_slice_to_core(slice: &[Self]) -> &[[T; $len]] {
56+
// SAFETY: `Self` is a `repr(transparent)` newtype for `[T; $len]`
57+
unsafe { core::slice::from_raw_parts(slice.as_ptr().cast(), slice.len()) }
58+
}
59+
60+
#[inline]
61+
fn cast_slice_to_core_mut(slice: &mut [Self]) -> &mut [[T; $len]] {
62+
// SAFETY: `Self` is a `repr(transparent)` newtype for `[T; $len]`
63+
unsafe { core::slice::from_raw_parts_mut(slice.as_mut_ptr().cast(), slice.len()) }
64+
}
65+
66+
#[inline]
67+
fn cast_slice_from_core(slice: &[[T; $len]]) -> &[Self] {
68+
// SAFETY: `Self` is a `repr(transparent)` newtype for `[T; $len]`
69+
unsafe { core::slice::from_raw_parts(slice.as_ptr().cast(), slice.len()) }
70+
}
71+
72+
#[inline]
73+
fn cast_slice_from_core_mut(slice: &mut [[T; $len]]) -> &mut [Self] {
74+
// SAFETY: `Self` is a `repr(transparent)` newtype for `[T; $len]`
75+
unsafe { core::slice::from_raw_parts_mut(slice.as_mut_ptr().cast(), slice.len()) }
76+
}
5377
}
5478
)+
5579
};

0 commit comments

Comments
 (0)