Rust可以调用抽象函数吗?

时间:2017-03-15 03:50:46

标签: rust traits

我在websocket库中发现了一些复杂的代码,似乎在Receiver特征中调用了一个抽象函数。

fn recv_message<'m, D, M, I>(&mut self) -> WebSocketResult<M>
    where M: Message<'m, D, DataFrameIterator = I>,
          I: Iterator<Item = D>,
          D: DataFrame
{
    let dataframes = try!(self.recv_message_dataframes());
    Message::from_dataframes(dataframes) // Isn't this an abstract function?
}

ws::Message特征的代码:

pub trait Message<'a, F>: Sized
    where F: DataFrame
{
    type DataFrameIterator: Iterator<Item = F>;
    fn from_dataframes<D>(frames: Vec<D>) -> WebSocketResult<Self> where D: DataFrame;
    fn dataframes(&'a self) -> Self::DataFrameIterator;
}

看起来它应该不起作用,因为Rust不知道要调用哪个函数。它是如何工作的?

1 个答案:

答案 0 :(得分:3)

关键是方法的签名:

fn from_dataframes<D>(frames: Vec<D>) -> WebSocketResult<Self>

当编译器统一类型时,它可以使用返回类型recv_message ie WebSocketResult<M>)来推断from_dataframes的结果必须是同一类型,这意味着有问题的Self类型为M,这意味着您真正的含义是:

<M as Message>::from_dataframes(dataframes)

如果实现类型和方法签名之间没有连接,那么它将无法工作,因为编译器没有任何基础可以作为其基础。