@@ -996,9 +996,9 @@ impl<T> [T] {
996
996
/// Returns an iterator over `N` elements of the slice at a time, starting at the
997
997
/// beginning of the slice.
998
998
///
999
- /// The chunks are slices and do not overlap. If `N` does not divide the length of the
1000
- /// slice, then the last up to `N-1` elements will be omitted and can be retrieved
1001
- /// from the `remainder` function of the iterator.
999
+ /// The chunks are array references and do not overlap. If `N` does not divide the
1000
+ /// length of the slice, then the last up to `N-1` elements will be omitted and can be
1001
+ /// retrieved from the `remainder` function of the iterator.
1002
1002
///
1003
1003
/// This method is the const generic equivalent of [`chunks_exact`].
1004
1004
///
@@ -1032,6 +1032,49 @@ impl<T> [T] {
1032
1032
ArrayChunks { iter : array_slice. iter ( ) , rem : snd }
1033
1033
}
1034
1034
1035
+ /// Returns an iterator over `N` elements of the slice at a time, starting at the
1036
+ /// beginning of the slice.
1037
+ ///
1038
+ /// The chunks are mutable array references and do not overlap. If `N` does not divide
1039
+ /// the length of the slice, then the last up to `N-1` elements will be omitted and
1040
+ /// can be retrieved from the `into_remainder` function of the iterator.
1041
+ ///
1042
+ /// This method is the const generic equivalent of [`chunks_exact_mut`].
1043
+ ///
1044
+ /// # Panics
1045
+ ///
1046
+ /// Panics if `N` is 0. This check will most probably get changed to a compile time
1047
+ /// error before this method gets stabilized.
1048
+ ///
1049
+ /// # Examples
1050
+ ///
1051
+ /// ```
1052
+ /// #![feature(array_chunks)]
1053
+ /// let v = &mut [0, 0, 0, 0, 0];
1054
+ /// let mut count = 1;
1055
+ ///
1056
+ /// for chunk in v.array_chunks_mut() {
1057
+ /// *chunk = [count; 2];
1058
+ /// count += 1;
1059
+ /// }
1060
+ /// assert_eq!(v, &[1, 1, 2, 2, 0]);
1061
+ /// ```
1062
+ ///
1063
+ /// [`chunks_exact_mut`]: #method.chunks_exact_mut
1064
+ #[ unstable( feature = "array_chunks" , issue = "74985" ) ]
1065
+ #[ inline]
1066
+ pub fn array_chunks_mut < const N : usize > ( & mut self ) -> ArrayChunksMut < ' _ , T , N > {
1067
+ assert_ne ! ( N , 0 ) ;
1068
+ let len = self . len ( ) / N ;
1069
+ let ( fst, snd) = self . split_at_mut ( len * N ) ;
1070
+ // SAFETY: We cast a slice of `len * N` elements into
1071
+ // a slice of `len` many `N` elements chunks.
1072
+ unsafe {
1073
+ let array_slice: & mut [ [ T ; N ] ] = from_raw_parts_mut ( fst. as_mut_ptr ( ) . cast ( ) , len) ;
1074
+ ArrayChunksMut { iter : array_slice. iter_mut ( ) , rem : snd }
1075
+ }
1076
+ }
1077
+
1035
1078
/// Returns an iterator over `chunk_size` elements of the slice at a time, starting at the end
1036
1079
/// of the slice.
1037
1080
///
@@ -5826,7 +5869,7 @@ unsafe impl<'a, T> TrustedRandomAccess for ChunksExactMut<'a, T> {
5826
5869
/// time), starting at the beginning of the slice.
5827
5870
///
5828
5871
/// When the slice len is not evenly divided by the chunk size, the last
5829
- /// up to `chunk_size -1` elements will be omitted but can be retrieved from
5872
+ /// up to `N -1` elements will be omitted but can be retrieved from
5830
5873
/// the [`remainder`] function from the iterator.
5831
5874
///
5832
5875
/// This struct is created by the [`array_chunks`] method on [slices].
@@ -5843,7 +5886,7 @@ pub struct ArrayChunks<'a, T: 'a, const N: usize> {
5843
5886
5844
5887
impl < ' a , T , const N : usize > ArrayChunks < ' a , T , N > {
5845
5888
/// Returns the remainder of the original slice that is not going to be
5846
- /// returned by the iterator. The returned slice has at most `chunk_size -1`
5889
+ /// returned by the iterator. The returned slice has at most `N -1`
5847
5890
/// elements.
5848
5891
#[ unstable( feature = "array_chunks" , issue = "74985" ) ]
5849
5892
pub fn remainder ( & self ) -> & ' a [ T ] {
@@ -5929,6 +5972,105 @@ unsafe impl<'a, T, const N: usize> TrustedRandomAccess for ArrayChunks<'a, T, N>
5929
5972
}
5930
5973
}
5931
5974
5975
+ /// An iterator over a slice in (non-overlapping) mutable chunks (`N` elements
5976
+ /// at a time), starting at the beginning of the slice.
5977
+ ///
5978
+ /// When the slice len is not evenly divided by the chunk size, the last
5979
+ /// up to `N-1` elements will be omitted but can be retrieved from
5980
+ /// the [`into_remainder`] function from the iterator.
5981
+ ///
5982
+ /// This struct is created by the [`array_chunks_mut`] method on [slices].
5983
+ ///
5984
+ /// [`array_chunks_mut`]: ../../std/primitive.slice.html#method.array_chunks_mut
5985
+ /// [`into_remainder`]: ../../std/slice/struct.ArrayChunksMut.html#method.into_remainder
5986
+ /// [slices]: ../../std/primitive.slice.html
5987
+ #[ derive( Debug ) ]
5988
+ #[ unstable( feature = "array_chunks" , issue = "74985" ) ]
5989
+ pub struct ArrayChunksMut < ' a , T : ' a , const N : usize > {
5990
+ iter : IterMut < ' a , [ T ; N ] > ,
5991
+ rem : & ' a mut [ T ] ,
5992
+ }
5993
+
5994
+ impl < ' a , T , const N : usize > ArrayChunksMut < ' a , T , N > {
5995
+ /// Returns the remainder of the original slice that is not going to be
5996
+ /// returned by the iterator. The returned slice has at most `N-1`
5997
+ /// elements.
5998
+ #[ unstable( feature = "array_chunks" , issue = "74985" ) ]
5999
+ pub fn into_remainder ( self ) -> & ' a mut [ T ] {
6000
+ self . rem
6001
+ }
6002
+ }
6003
+
6004
+ #[ unstable( feature = "array_chunks" , issue = "74985" ) ]
6005
+ impl < ' a , T , const N : usize > Iterator for ArrayChunksMut < ' a , T , N > {
6006
+ type Item = & ' a mut [ T ; N ] ;
6007
+
6008
+ #[ inline]
6009
+ fn next ( & mut self ) -> Option < & ' a mut [ T ; N ] > {
6010
+ self . iter . next ( )
6011
+ }
6012
+
6013
+ #[ inline]
6014
+ fn size_hint ( & self ) -> ( usize , Option < usize > ) {
6015
+ self . iter . size_hint ( )
6016
+ }
6017
+
6018
+ #[ inline]
6019
+ fn count ( self ) -> usize {
6020
+ self . iter . count ( )
6021
+ }
6022
+
6023
+ #[ inline]
6024
+ fn nth ( & mut self , n : usize ) -> Option < Self :: Item > {
6025
+ self . iter . nth ( n)
6026
+ }
6027
+
6028
+ #[ inline]
6029
+ fn last ( self ) -> Option < Self :: Item > {
6030
+ self . iter . last ( )
6031
+ }
6032
+
6033
+ unsafe fn get_unchecked ( & mut self , i : usize ) -> & ' a mut [ T ; N ] {
6034
+ // SAFETY: The safety guarantees of `get_unchecked` are transferred to
6035
+ // the caller.
6036
+ unsafe { self . iter . get_unchecked ( i) }
6037
+ }
6038
+ }
6039
+
6040
+ #[ unstable( feature = "array_chunks" , issue = "74985" ) ]
6041
+ impl < ' a , T , const N : usize > DoubleEndedIterator for ArrayChunksMut < ' a , T , N > {
6042
+ #[ inline]
6043
+ fn next_back ( & mut self ) -> Option < & ' a mut [ T ; N ] > {
6044
+ self . iter . next_back ( )
6045
+ }
6046
+
6047
+ #[ inline]
6048
+ fn nth_back ( & mut self , n : usize ) -> Option < Self :: Item > {
6049
+ self . iter . nth_back ( n)
6050
+ }
6051
+ }
6052
+
6053
+ #[ unstable( feature = "array_chunks" , issue = "74985" ) ]
6054
+ impl < T , const N : usize > ExactSizeIterator for ArrayChunksMut < ' _ , T , N > {
6055
+ fn is_empty ( & self ) -> bool {
6056
+ self . iter . is_empty ( )
6057
+ }
6058
+ }
6059
+
6060
+ #[ unstable( feature = "trusted_len" , issue = "37572" ) ]
6061
+ unsafe impl < T , const N : usize > TrustedLen for ArrayChunksMut < ' _ , T , N > { }
6062
+
6063
+ #[ unstable( feature = "array_chunks" , issue = "74985" ) ]
6064
+ impl < T , const N : usize > FusedIterator for ArrayChunksMut < ' _ , T , N > { }
6065
+
6066
+ #[ doc( hidden) ]
6067
+ #[ unstable( feature = "array_chunks" , issue = "74985" ) ]
6068
+ unsafe impl < ' a , T , const N : usize > TrustedRandomAccess for ArrayChunksMut < ' a , T , N > {
6069
+ fn may_have_side_effect ( ) -> bool {
6070
+ false
6071
+ }
6072
+ }
6073
+
5932
6074
/// An iterator over a slice in (non-overlapping) chunks (`chunk_size` elements at a
5933
6075
/// time), starting at the end of the slice.
5934
6076
///
0 commit comments