Rust 如何理解仅使用 FromIterator::from_iter 调用 from_iter 的适当实现?
How does Rust understand to call the appropriate implementation of from_iter using only FromIterator::from_iter?
如果集合实现了 FromIterator
.
,则可以使用 Iterator
特征的 collect
方法将迭代器转换为集合
let vec = (0..10).collect::<Vec<_>>();
let devec = (0..10).collect::<VecDeque<_>>();
Vec
和 VecDeque
实现 FromIterator
特征。
Iterator::collect
方法的实现是:
fn collect<B: FromIterator<Self::Item>>(self) -> B
where
Self: Sized,
{
FromIterator::from_iter(self)
}
Rust 如何理解从 FromIterator::from_iter(self)
调用 Vec
或 VecDeque
的 from_iter
方法?
当 FromIterator
特征有一个实现者时,它的形式是:
impl<T> FromIterator for Vec<T> {
fn from_iter<I>(iter: I) -> Vec<T> { /* ... */ }
}
它returns具体类型Self
;那就是 collect
代码中的通用参数 B
。
当您键入 collect::<Vec<_>>()
时,您说 B
是 Vec<_>
,因此,必须调用 Vec<_>::from_iter()
。
collect
的实现本可以写成:<B as FromIterator>::from_iter(self)
,但更冗长。
让我们看看FromIterator
特征的定义:
pub trait FromIterator<A>: Sized {
fn from_iter<T: IntoIterator<Item = A>>(iter: T) -> Self;
}
从 FromIterator::from_iter()
在 collect()
方法的实现中的使用方式,Rust 知道对 FromIterator::from_iter()
的调用将迭代器 self
作为参数,并且 returns 类型为 B
的对象。此信息与 from_iter()
方法的定义相匹配,因此 Rust 可以得出结论 FromIterator
特征实现的 Self
类型必须是 B
,并且类型 A
必须是迭代器的项类型。 FromIterator
特征的 Self
类型正是 Rust 需要调用 from_iter()
的类型。
类型推断如何工作的细节很复杂。 Rust 使用 Hindley-Milner 类型推理算法的变体。您可以在 this document from the rustc guide.
中找到更多信息
粗略地说,Rust 使用它拥有的关于未知类型的所有信息作为约束,并迭代地改进它关于泛型类型的知识,直到每个未知类型只剩下一个类型,或者某些类型仍然不明确。在前一种情况下,类型推断成功并且已经推断出所有类型,而在后一种情况下,Rust 将抛出一个错误,指出它需要进一步的类型注释。
如果集合实现了 FromIterator
.
Iterator
特征的 collect
方法将迭代器转换为集合
let vec = (0..10).collect::<Vec<_>>();
let devec = (0..10).collect::<VecDeque<_>>();
Vec
和 VecDeque
实现 FromIterator
特征。
Iterator::collect
方法的实现是:
fn collect<B: FromIterator<Self::Item>>(self) -> B
where
Self: Sized,
{
FromIterator::from_iter(self)
}
Rust 如何理解从 FromIterator::from_iter(self)
调用 Vec
或 VecDeque
的 from_iter
方法?
当 FromIterator
特征有一个实现者时,它的形式是:
impl<T> FromIterator for Vec<T> {
fn from_iter<I>(iter: I) -> Vec<T> { /* ... */ }
}
它returns具体类型Self
;那就是 collect
代码中的通用参数 B
。
当您键入 collect::<Vec<_>>()
时,您说 B
是 Vec<_>
,因此,必须调用 Vec<_>::from_iter()
。
collect
的实现本可以写成:<B as FromIterator>::from_iter(self)
,但更冗长。
让我们看看FromIterator
特征的定义:
pub trait FromIterator<A>: Sized {
fn from_iter<T: IntoIterator<Item = A>>(iter: T) -> Self;
}
从 FromIterator::from_iter()
在 collect()
方法的实现中的使用方式,Rust 知道对 FromIterator::from_iter()
的调用将迭代器 self
作为参数,并且 returns 类型为 B
的对象。此信息与 from_iter()
方法的定义相匹配,因此 Rust 可以得出结论 FromIterator
特征实现的 Self
类型必须是 B
,并且类型 A
必须是迭代器的项类型。 FromIterator
特征的 Self
类型正是 Rust 需要调用 from_iter()
的类型。
类型推断如何工作的细节很复杂。 Rust 使用 Hindley-Milner 类型推理算法的变体。您可以在 this document from the rustc guide.
中找到更多信息粗略地说,Rust 使用它拥有的关于未知类型的所有信息作为约束,并迭代地改进它关于泛型类型的知识,直到每个未知类型只剩下一个类型,或者某些类型仍然不明确。在前一种情况下,类型推断成功并且已经推断出所有类型,而在后一种情况下,Rust 将抛出一个错误,指出它需要进一步的类型注释。