我在第一部分中有一个项目项和一个索引项,从本质上讲,我给了我要修改的项目子组。要遍历项目并进行操作,我可以创建以下帮助函数。
fn process_things_by_index_loop<T>(things: &mut [T], indices: &[usize], f: &dyn Fn(&mut T)) {
for &ix in indices {
let t = &mut things[ix];
f(t);
}
}
这很好用,但我实际上只是想对这些项目进行迭代,以便在进行进一步处理之前可以对它们应用例如过滤器。
看起来这可能只是索引到项的映射,如下所示:
fn iterate_thigns<'a, T>(
things: &'a mut [T],
indices: &'a [usize],
) -> impl Iterator<Item = &'a mut T> {
indices.iter().map(|&ix| -> &mut T { &mut things[ix] })
}
这当然是行不通的,因为我可以在索引切片中拥有两次相同的索引,并且在收集迭代器时,我将创建对同一项目的两个可变引用。因此,这适当地给出了生命周期错误:
error[E0495]: cannot infer an appropriate lifetime for lifetime parameter in function call due to conflicting requirements
--> src\main.rs:4:47
|
4 | indices.iter().map(|&ix|-> &mut T { &mut things[ix]})
| ^^^^^^^^^^
|
error[E0495]: cannot infer an appropriate lifetime for lifetime parameter in function call due to conflicting requirements
--> src\main.rs:4:47
|
4 | indices.iter().map(|&ix|-> &mut T { &mut things[ix]})
| ^^^^^^^^^^
|
note: first, the lifetime cannot outlive the lifetime '_ as defined on the body at 4:24...
--> src\main.rs:4:24
|
4 | indices.iter().map(|&ix|-> &mut T { &mut things[ix]})
| ^^^^^^^^^^^^^^^
note: ...so that reference does not outlive borrowed content
--> src\main.rs:4:47
|
4 | indices.iter().map(|&ix|-> &mut T { &mut things[ix]})
| ^^^^^^
note: but, the lifetime must be valid for the lifetime 'a as defined on the function body at 3:19...
--> src\main.rs:3:19
|
3 | fn iterate_thigns<'a, T>(things: &'a mut [T], indices: &'a [usize]) -> impl Iterator<Item=&'a mut T>{
| ^^
= note: ...so that the types are compatible:
expected &mut T
found &'a mut T
这也意味着返回类型可能根本不是简单的Iterator
。
这个问题似乎也与this blog post from 2013 on "Iterators yielding mutable references"有关,asking about mutable multi threaded access to the content of a vector指出该模式尚无标准解决方案。
还有一个相关的问题Here's the Sandbox,但我对单线程,类似迭代器的解决方案非常感兴趣,该解决方案甚至可能允许索引重复。
那么,是否有某种东西可以启用类似迭代器的接口,以对索引指示的项目进行顺序迭代?