我认为,对于一个向量进行迭代时,循环体不应该随意改变向量。这可以防止迭代器失效,从而避免出现错误。
然而,并非所有类型的改变都会导致迭代器失效。请看以下示例:
let mut my_vec: Vec<Vec<i32>> = vec![vec![1,2], vec![3,4], vec![5,6]];
for inner in my_vec.iter_mut() { // <- or .iter()
// ...
my_vec[some_index].push(inner[0]); // <-- ERROR
}
这样的变异不会使
my_vec
的迭代器无效,但是它是被禁止的。它可能会使my_vec[some_index]
中特定元素的任何引用无效,但我们不使用任何这样的引用。我知道这些问题很常见,我不需要解释。我正在寻找一种重构方式,以便我可以摆脱这个循环。在我的实际代码中,我有一个庞大的循环体,除非我漂亮地表达这一点,否则我无法模块化它。
到目前为止,我想到了以下几点:
1.用
Rc<RefCell<...>>
包装向量。我认为这仍然会在运行时失败,因为RefCell
将被迭代器借用,当循环体尝试借用它时,它将失败。2.使用临时向量累积未来的推送,并在循环结束后推送它们。这还不错,但需要比即时推送更多的分配。
3.不安全的代码和指针操作。
4.
Iterator
文档中列出的任何内容都没有帮助。我查看了itertools,看起来它也没有帮助。5.使用
while
循环和索引,而不是使用迭代器利用对外部向量的引用。这还不错,但不能让我使用迭代器和适配器。我只想摆脱这个外部循环并使用my_vec.foreach(...)
。是否有任何习惯用法或库可以让我漂亮地做到这一点?不安全的函数可以,只要它们不向我公开指针。
some_index
是常量吗?还是可以预测的? - Matthieu M.inner
的具体内容。 - loudandclear