Currently, if you want to create array for array types at runtime, the best practice is to create [MaybeUninit<T>; N]
first and then initialize it by for loops, and finally use unsafe std::mem::transmute
, according to docs of MaybeUninit<T>
. Although this pattern is efficient and practical, it is not elegant and not easy to use, and it needs to use unsafe
which maybe scares people.
Thus, I proposed to add a serial of construct functions for [T;N], after the shipping of the const generics. The proposed definition maybe:
impl<T, const usize N> for [T; N] {
// create an array filled with any val that can be cloned
fn new_with(val :T) -> [T; N] where T: Clone;
// and more generally
// create an array by a factory function returns T
fn new_by(f: F) -> [T; N] where F: FnMut() -> T;
}
Alternatives:
-
The function names should be discussed to be more nature and elegant, because there is no similar constructors for containers before. Alternative names should be considered for better naming conversion.
-
new_by
function takes iterators, instead of functions.Or a bigger but more general change:
add a
TryFromIterator
trait, just likeTryFrom
andFrom
. -
Furthermore, these functions may be used in const context. This is helpful when generating a building-time look-up array for some algorithms. For this purpose, a construction function taking function with index is more useful, for example:
// This function takes a function with index of current item, // so it can generate different items at different positions. const fn new_by_index(f: F) -> [T; N] where F: FnMut(usize) -> T;
This function should be further discussed, because there is no similar function before.
-
This initializer may benefit other containers, such as
Vec
. And it is more familiar for people who use c++ before, becausestd::vector
can also be construct with N of T items.
Finally, I believe this change can improve array usability for everyone, however, more discussions may be required, and the detailed interface should be rechecked.