5

我有一个实现的结构,Iterator它可以作为迭代器正常工作。它产生值,并使用.map(),我从本地 HTTP 服务器下载每个项目并保存结果。我现在想并行化这个操作,Rayon看起来很友好。

尝试按照文档中的示例进行操作时出现编译器错误。

这是按顺序工作的代码。generate_values返回实现的结构Iteratordl下载值并保存它们(即它有副作用)。由于迭代器在 Rust 中是惰性的,所以我.count()在末尾放了 a 以便它实际运行它。

generate_values(14).map(|x| { dl(x, &path, &upstream_url); }).count();

在人造丝示例之后,我尝试了这个:

generate_values(14).par_iter().map(|x| { dl(x, &path, &upstream_url); }).count();

并得到以下错误:

src/main.rs:69:27: 69:37 error: no method named `par_iter` found for type `MyIterator` in the current scope

有趣的是,当我使用.iter()许多 Rust 东西使用的 时,我得到了一个类似的错误:

src/main.rs:69:27: 69:33 error: no method named `iter` found for type `MyIterator` in the current scope
src/main.rs:69     generate_values(14).iter().map(|tile| { dl_tile(tile, &tc_path, &upstream_url); }).count();

既然我实施了Iterator,我应该.iter()免费获得吧?这是为什么.par_iter()不起作用?

Rust 1.6 和 Rayon 0.3.1

$ rustc --version
rustc 1.6.0 (c30b771ad 2016-01-19)
4

2 回答 2

7

人造丝 0.3.1 定义par_iter为:

pub trait IntoParallelRefIterator<'data> {
    type Iter: ParallelIterator<Item=&'data Self::Item>;
    type Item: Sync + 'data;

    fn par_iter(&'data self) -> Self::Iter;
}

Rayon 本身只有一种类型实现了这个特性[T]

impl<'data, T: Sync + 'data> IntoParallelRefIterator<'data> for [T] {
    type Item = T;
    type Iter = SliceIter<'data, T>;

    fn par_iter(&'data self) -> Self::Iter {
        self.into_par_iter()
    }
}

这就是为什么Lukas Kallbertodt 对遗嘱的回答collect奏效VecVec对切​​片的取消引用。

一般来说,Rayon 不能假设任何迭代器都适合并行化,因此它不能默认包含所有Iterators。

既然你已经定义generate_values了,你也可以为它实现适当的 Rayon 特征:

  1. IntoParallelIterator
  2. IntoParallelRefIterator
  3. IntoParallelRefMutIterator

这应该可以让您避免收集到临时向量中。

于 2016-03-08T14:09:29.660 回答
6

不,Iterator特征与方法无关iter()。是的,这有点令人困惑。

这里有几个不同的概念。AnIterator是一种可以吐出值的类型;它只需要实现next()并且有许多其他方法,但这些都不是iter()。然后是IntoIterator说可以将类型转换为Iterator. 这个特质有into_iter()方法。现在,该iter()方法与这两个特征中的任何一个都没有真正的关系。这只是许多类型的普通方法,通常类似于into_iter().

现在到您的人造丝问题:看起来您不能只使用任何普通的迭代器并将其变成并行迭代器。但是,我从来没有使用过这个库,所以对它持保留态度。对我来说,您似乎需要将迭代器收集到 aVec中才能使用par_iter().

请注意:使用普通迭代器时,不应使用map()and count(),而应使用标准for循环。

于 2016-03-08T10:03:06.907 回答