Home > database >  How can I allocate a very large sized array?
How can I allocate a very large sized array?

Time:10-30

Because I am dealing with an environment with certain memory constraints, I need to allocate a very large statically sized array at the beginning of my program's execution:

let mut data: [Foo; 1024] = ?

How can I initialize this array with "empty" data?

I have tried using the default method, since Foo also has a default:

let mut data: [Foo; 1024] = Default::default(),

but it doesn't work, because array only implements default for a fixed set of sizes:

error[E0277]: the trait bound `[foo::Foo; 1024]: std::default::Default` is not satisfied
   --> /src/foo.rs:143:22
    |
143 |           = Default::default(),
    |                      ^^^^^^^^^^^^^^^^ the trait `std::default::Default` is not implemented for `[foo::Foo; 1024]`
    |
    = help: the following other types implement trait `std::default::Default`:
              &[T]
              &mut [T]
              [T; 0]
              [T; 10]
              [T; 11]
              [T; 12]
              [T; 13]
              [T; 14]
            and 27 others

How can I initialize such a large statically sized array without typing a giant literal in my code?

CodePudding user response:

To repeat some data in an array several times we use [{data}; {times}]. So you need this:

let mut data = [Foo::default(); 1024];

Annotation here is unnecessary because we specified type and length in variable’s value.

CodePudding user response:

Thanks to the documentation of MaybeUninit, we can provide our own way to initialise this array.

Obviously, this is only useful if you don't want Foo to implement Copy, otherwise the trivial usual notation ([value; repeat]) applies (but the question probably wouldn't have been asked ;^)

use std::mem::MaybeUninit;

struct Foo {
    a: u8,
    b: u8,
}

fn main() {
    let data: [Foo; 1024] = {
        let mut data: [MaybeUninit<Foo>; 1024] =
            unsafe { MaybeUninit::uninit().assume_init() };
        for f in data.iter_mut() {
            f.write(Foo { a: u8::MAX, b: 0 });
        }
        unsafe { std::mem::transmute(data) }
    };
    for f in data.iter() {
        assert_eq!(f.a, u8::MAX);
        assert_eq!(f.b, 0);
    }
}
  • Related