If I write a function that takes one argument of type [f32] (as opposed to e.g. &[f32]), I get an error:
the trait bound `[f32]: std::marker::Sized` is not satisfied
The docs say this is because [f32] does not have a compile-time-known size. A reasonable limitation. Fair enough.
However, there is at least one function in the standard library with this type. Here's me calling it:
let b: Box<[f32]> = Box::new([1.0, 2.0, 3.0]);
How come this is allowed in the standard library and not in my code? What is the relevant difference? (There's no obvious magic in the source).
[f32]is unsized. However,[1.0, 2.0, 3.0]is sized... its type is[f32; 3].That's what
Twill be when compiled with the standard library code, an[f32; 3]sized array.To accept a sized array yourself, you can do the same:
Click here to see a working sample on the Playground
An
&[f32]slice is sized too.. which is why it is allowed also.As Lukas points out in the comments, slices are a "fat pointer" (You can read about Dynamically Sized Types in the Nomicon). Slice fat pointers consist of a pointer to a piece of data and a value representing how big that data is.