Rust - Advanced Trait - Trait Method Direct Call

Recently, I've been diving into the serde library, and when it comes to the from-trait method, I find it quite puzzling. It seems to attempt to call deserialize on the trait de::Deserialize and pass in a deserializer, but I'm unsure how Rust determines which concrete type the deserialize method will be called on ? What concept in rust facilitates that ?

fn from_trait<'de, R, T>(read: R) -> Result<T>
where
    R: Read<'de>,
    T: de::Deserialize<'de>,
{
    let mut de = Deserializer::new(read);
    let value = tri!(de::Deserialize::deserialize(&mut de));

    // Make sure the whole stream has been consumed.
    tri!(de.end());
    Ok(value)
}
pub trait Deserialize<'de>: Sized {
    /// Deserialize this value from the given Serde deserializer.
    ///
    /// See the [Implementing `Deserialize`][impl-deserialize] section of the
    /// manual for more information about how to implement this method.
    ///
    /// [impl-deserialize]: https://serde.rs/impl-deserialize.html
    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
    where
        D: Deserializer<'de>;

I can't find this method in Serde code base, so all of the following is mostly guessing, but probably right.


This is simply type inference.

from_trait returns Result<T> - here, Result is a type alias to something like Result<T, serde::Error>. That is, we know that Ok(value) at the end of the function is of type Result<T, _>, and therefore value is of type T. Then, Deserialize::deserialize returns Result<Self, _>, and tri! macro unwraps this Result to get Self, which is then assigned to value; therefore, this Self (i.e. the type method is called on) is T, too.

2 Likes

Actually, I'm reading this one. So, Rust also performs type inference on traits as well.

Why wouldn't it?

This topic was automatically closed 90 days after the last reply. We invite you to open a new topic if you have further questions or comments.