Trait wyz::conv::Conv

source · []
pub trait Conv: Sized {
    fn conv<T: Sized>(self) -> T
    where
        Self: Into<T>
, { ... } }
Expand description

Directed Type Conversion

This trait is an accessory to From and Into. It works by moving the destination type from the trait name (Into<Target>::into) into the method name (Conv::conv::<Target>). This change makes Into<_> the correct trait to use in trait bounds and .conv::<_> the correct method to use in expressions.

A conv::<T> method is automatically available whenever an Into<T> implementation exists for a type. Into<T> is most commonly implemented by taking advantage of the reflexive blanket implentation using From, but can also be manually implemented as desired.

.into() cannot be used in intermediate expressions, because it is impossible for the compiler’s type engine to select a unique Into<T> implementation. This means that expressions like v.into().use() will never compile. Users can replace .into() with .conv::<Dest>() in order to inform the compiler of the type of the expression after the conversion, and make compilation succeed.

Conv cannot be used in trait bounds, because the trait itself is not generic. All Sized types implement Conv by default, so specifying that a type must be Conv adds no information to the solver.

Examples

Conversion as methods

Conversion with .into() will fail to compile, even with the type annotation:

let s: String = "static".into().clone();
//              ^^^^^^^^^^^^^^^ cannot infer type for `T`
// note: type must be known at this point

while the equivalent code with .conv::<_> does compile:

let s = "static".conv::<String>().clone();

Conversion as traits

Bounding a type with Conv will not compile, because the trait itself gives no information:

fn lift<T: Conv>(src: T) -> String {
  src.conv::<String>().clone()
//    ^^^^ the trait `From<T>` is not implemented for `String`
// help: consider adding a `where String: From<T>` bound
// note: required because of the requirements on the impl of `Into<String>` for `T`
}

This can be fixed by adding the clause where String: From<T>, or by using the bound Into:

fn lift<T: Into<String>>(src: T) -> String {
  src.conv::<String>().clone()
}

The Into<T> trait bound makes available both the Into::<T>::into method and the Conv::conv::<T> method.

Provided methods

Converts self into a target type.

This method runs <Self as Into<T>>::into on self to produce the desired output. The only difference between using Conv::conv and Into::into is where the target type is placed in the name; .conv() can be used in intermediate positions of an expression, while .into() cannot.

Examples
use wyz::conv::Conv;

let t = "hello".conv::<String>();

Implementors