Macro trait_ext

Source
pub macro trait_ext($vis:vis trait $ident:ident for $($ident2:path),+ { $($item:item)* }) {
    ...
}
Expand description

Specify a trait which automatically is implemented for each type that implements the super trait.

The quantificator of implementation makes sure you can’t provide any other implementation (without negative reasoning or specialization at least). This forbids reimplementing methods.

§Example use

trait_ext! {
  pub trait SampleExt for std::fmt::Debug {
    fn test(&self) -> {
      eprintln!("{:?}", self)
    }
  }
}

fn foo<T: std::fmt::Debug>(value: T) -> () {
  value.test(); // is implemented automatically
}

§Interesting fact

This almost replicates the inherent implementations in Rust. Inherent implementations by their nature are basically unnamed traits with more specific algorithm on finding the implementation in the scope.

Each inherent impl block is basically an unnamed trait which is attached to the type the impl is implemented for.

For instance:

struct Foo;

impl Foo { fn first(&self) -> () {} }
impl Foo { fn second(&self) -> () {} }

Is semantically equivalent to:

struct Foo;
trait Foo1 { fn first(&self) -> (); }
impl Foo1 for Foo { fn first(&self) -> () {} }
trait Foo2 { fn first(&self) -> (); }
impl Foo2 for Foo { fn second(&self) -> () {} }

This macro is very simple an replicates this inherent impl logic.