Parallel processing 无法使用人造丝';s`.par_iter()`
我有一个实现Parallel processing 无法使用人造丝';s`.par_iter()`,parallel-processing,iterator,rust,rayon,Parallel Processing,Iterator,Rust,Rayon,我有一个实现迭代器的结构,它可以作为迭代器很好地工作。它生成值,并使用.map(),从本地HTTP服务器下载每个项目并保存结果。我现在想并行这个操作,看起来很友好 我在尝试遵循文档中的示例时遇到了一个编译器错误 这是按顺序工作的代码generate_values返回实现迭代器的结构dl下载值并保存它们(即它有副作用)。因为迭代器在Rust中是惰性的,所以我在末尾放了一个.count(),以便它实际运行它 generate_values(14).map(|x| { dl(x, &path,
迭代器的结构,它可以作为迭代器很好地工作。它生成值,并使用.map()
,从本地HTTP服务器下载每个项目并保存结果。我现在想并行这个操作,看起来很友好
我在尝试遵循文档中的示例时遇到了一个编译器错误
这是按顺序工作的代码generate_values
返回实现迭代器的结构dl
下载值并保存它们(即它有副作用)。因为迭代器在Rust中是惰性的,所以我在末尾放了一个.count()
,以便它实际运行它
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()
时,我得到了一个类似的错误:
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();
既然我实现了迭代器
,我应该免费获得.iter()
,对吗?这就是为什么.par_iter()
不起作用的原因吗
锈1.6和人造丝0.3.1
$ rustc --version
rustc 1.6.0 (c30b771ad 2016-01-19)
不,迭代器特性与iter()方法无关。是的,这有点令人困惑
这里有一些不同的概念。迭代器是一种可以吐出值的类型;它只需要实现next()
,还有许多其他方法,但没有一种是iter()
。然后是IntoIterator
,它表示可以将类型转换为Iterator
。这个特性有进入iter()的方法。现在,iter()
方法实际上与这两个特性中的任何一个都没有关系。这只是许多类型的一种普通方法,其工作原理通常类似于into\u iter()
现在来看看你的人造丝问题:看起来你不能只使用普通的迭代器,然后把它变成一个并行的迭代器。然而,我从未使用过这个库,所以对此持保留态度。在我看来,您需要将迭代器收集到Vec
中才能使用par_iter()
需要注意的是:在使用普通迭代器时,不应使用map()
和count()
,而应使用标准进行循环。人造丝0.3.1定义为:
这就是为什么收集到Vec
会起作用<代码>矢量控制
取消对切片的引用
通常,Rayon不能假设任何迭代器都可以并行化,因此它不能默认包含所有迭代器
由于您已经定义了生成_值
,因此也可以为其实现适当的人造丝特征:
into并行迭代器
into并行重新安装器
IntoParallelRefMultierator
这应该可以避免收集到一个临时向量。如果没有代码,我们就无能为力了:(您是否有一个小的(简化的)示例来展示这个问题?我最初使用了for循环。我只将其作为.map().count()
编写,这样我就可以使用.par_iter()
。我已经假设:)我只是想向未来的读者说明这一点,因为人们很容易陷入“迭代器太棒了——迭代器适配器适合所有东西”的心态,就像我一样^_^
pub trait IntoParallelRefIterator<'data> {
type Iter: ParallelIterator<Item=&'data Self::Item>;
type Item: Sync + 'data;
fn par_iter(&'data self) -> Self::Iter;
}
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()
}
}