Traits
A trait names some behavior. Many different types can share that behavior.
Defining a trait
A trait lists method signatures. It ends each signature with ; instead of a body.
trait Speak { fn speak(&self) -> String;}Implementing a trait
impl Trait for Type gives a type the trait's methods. Then you call them like normal methods.
struct Dog;impl Speak for Dog { fn speak(&self) -> String { String::from("woof") }}// Dog.speak() returns "woof"struct Dog; is a unit struct: a struct with no fields. Its only value is written Dog, so you call Dog.speak(). Each type writes its own body, so Cat can return "meow" from the same method. You can also implement your own trait for a built-in type, like impl Speak for i32. A trait impl may only hold the trait's methods; an extra one is error E0407. Put other methods in a plain impl Dog block.
Default methods
A trait method can have a body. That body is the default. A type gets it for free, or writes its own version to override it.
trait Greet { fn name(&self) -> String; fn hello(&self) -> String { format!("Hello, {}", self.name()) }}A type that implements Greet only has to write name. A default method can call the other methods of the trait.
Missing trait items
An impl must provide every method that has no default. If one is missing, the code fails with error E0046.
impl Greet for Dog {}// error E0046: missing `name`You can leave out methods that have a default.
Remember
- A trait is a list of methods a type promises to have.
impl Trait for Type { ... }keeps that promise.- Methods with a body are defaults; you may override them.
- E0046 means "your impl is missing a required method".