'How can I fix the error E0277: the trait bound `[usize]: std::marker::Sized` is not satisfied?

I'm trying to pass an array to a function:

fn my_func(xs: [usize]) -> usize {
    0
}

fn main() {
    let arr = [329, 457, 657];
    let res = my_func(inp);
}

I get the error:

error[E0277]: the trait bound `[usize]: std::marker::Sized` is not satisfied
 --> src/main.rs:1:12
  |
1 | fn my_func(xs: [usize]) -> usize {
  |            ^^ `[usize]` does not have a constant size known at compile-time
  |
  = help: the trait `std::marker::Sized` is not implemented for `[usize]`
  = note: all local variables must have a statically known size

I know about these other questions but they don't seem to apply to my simple situation.

How can I fix the error?



Solution 1:[1]

I'm trying to pass an array to a function

fn my_func(xs: [usize])

This is not an array, it's a slice; that's the problem. Read What is the difference between a slice and an array?

As the other answers mention, there are several potential avenues to solve the problem, depending on your goals:

  • Slices ([T]) don't have a size
  • Arrays ([T; N]) have a size
  • References to slices (&[T]) have a size
  • Boxed slices (Box<[T]>) have a size
  • References to arrays (&[T; N]) have a size

and so on.

Solution 2:[2]

Your problem (and the reason why a & fixes your problem) is, that a slice has no known size at compile time.

There are several solutions:

  1. Use an explicit length

    fn foo(arr: [usize; 3]) { }
    

Using an explicit length will tell the compiler how large the array is and can now decide how much space to reserve for the array.

  1. Use a reference

    fn foo(arr: &[usize]) { }
    

A reference points to the slice (a fat pointer in fact), which size is known at compile time (depends on your architecture, but typically 32/64 bit).

  1. Use heap allocation

    fn foo(arr: Box<[usize]> { }
    

A box is a heap allocated element (in fact a pointer), so that size is known as well.

There are other container (Rc, Arc, ...) which accept a unsized element. You can spot them in the source code easily, because they have a requirement ?Sized for their template argument (see Box example).

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 Community
Solution 2