What is the trait `core::kinds::Sized` is not impl

2019-04-09 16:15发布

问题:

I expected this to work:

trait Task<R, E> {
  fn run(&self) -> Result<R, E>;
}

mod test {

  use super::Task;

  struct Foo;
  impl<uint, uint> Task<uint, uint> for Foo {
    fn run(&self) -> Result<uint, uint> {
      return Err(0);
    }
  }

  fn can_have_task_trait() {
    Foo;
  }
}

fn main() {
  test::can_have_task_trait();
}

...but it does not:

<anon>:10:3: 14:4 error: the trait `core::kinds::Sized` is not implemented for the type `<generic #0>`
<anon>:10   impl<uint, uint> Task<uint, uint> for Foo {
<anon>:11     fn run(&self) -> Result<uint, uint> {
<anon>:12       return Err(0);
<anon>:13     }
<anon>:14   }
<anon>:10:3: 14:4 note: the trait `core::kinds::Sized` must be implemented because it is required by `Task`
<anon>:10   impl<uint, uint> Task<uint, uint> for Foo {
<anon>:11     fn run(&self) -> Result<uint, uint> {
<anon>:12       return Err(0);
<anon>:13     }
<anon>:14   }
<anon>:10:3: 14:4 error: the trait `core::kinds::Sized` is not implemented for the type `<generic #1>`
<anon>:10   impl<uint, uint> Task<uint, uint> for Foo {
<anon>:11     fn run(&self) -> Result<uint, uint> {
<anon>:12       return Err(0);
<anon>:13     }
<anon>:14   }
<anon>:10:3: 14:4 note: the trait `core::kinds::Sized` must be implemented because it is required by `Task`
<anon>:10   impl<uint, uint> Task<uint, uint> for Foo {
<anon>:11     fn run(&self) -> Result<uint, uint> {
<anon>:12       return Err(0);
<anon>:13     }
<anon>:14   }
error: aborting due to 2 previous errors
playpen: application terminated with error code 101
Program ended.

playpen: http://is.gd/kxDt0P

So, what's going on?

I have no idea what this error means.

Is it that I'm using Result and that requires that U, V are not Sized? In which case, why are they Sized? I didn't write:

Task<Sized? R, Sized? E>

Are all generics now dynamically sized or something? (in which case, what does Sized? even mean?)

What's going on?

回答1:

You just need to remove the <uint, uint> in impl<uint, uint>, because type parameters go there and not concrete types:

impl Task<uint, uint> for Foo { ... }

I think the errors you're getting are the compiler getting confused over unused type parameters. It also occurs with this super-reduced version:

trait Tr {}
impl<X> Tr for () {}


回答2:

Rust does not provide « Generics specialization » : you defined your trait as Task<R, E>, you must implement it using generic types (R and E).

It is not possible to implement it with only specific types like you are trying to do with <uint, uint>.

For example, if you wrote :

trait Foo<R> {}

struct Bar;

struct Baz;

impl<Baz> Foo<Baz> for Bar {}

You should not expect the Baz in you implementation bloc to be the same as your struct Baz : it is being shadowed, just like a var argument of a function would shadow a var global variable.

Yet, when you do this with a primitive type, yet get this cryptic error message rather than simple shadowing, this is probably a bug, either you should have shadowing or a more clear error message.



标签: rust