我正在尝试编写一个解析器,将迭代器通过向量传递给函数。代码类似这样:
fn foo(itr : ???) {
while let Some(c) = itr.next() {
if *c != 0 {
break;
}
println!("{}", *c);
}
}
fn main() {
let v = vec![0; 10];
let itr = v.iter();
while let Some(c) = itr.next() {
foo(itr);
}
}
我不确定如何在向量上写迭代器的类型。我试着输入错误的类型 u32
看看是什么类型rustc
预期:core::slice::Iter<'_, _>
.当我尝试使用 core::slice
rustc 提示 Use of undeclared type or module 'core::slice'
最佳答案
迭代器有很多种;大多数时候,您真正想要的是一个能够使用其中任何一个的函数。为此,惯用的解决方案是使用泛型。
fn foo<'a, T: Iterator<Item=&'a i32>>(mut itr: T) {
while let Some(c) = itr.next() {
if *c != 0 {
break;
}
println!("{}", *c);
}
}
fn main() {
let v = vec![0; 10];
let mut itr = v.iter();
while let Some(c) = itr.next() {
foo(itr);
}
}
虽然上面的代码没有编译,因为它将 itr
移动到 foo
中,然后尝试在 while let
上再次使用它.为了解决这个问题,我们需要改为通过引用传递迭代器。
fn foo<'a, T: Iterator<Item=&'a i32>>(itr: &mut T) {
while let Some(c) = itr.next() {
if *c != 0 {
break;
}
println!("{}", *c);
}
}
fn main() {
let v = vec![0; 10];
let mut itr = v.iter();
while let Some(c) = itr.next() {
foo(&mut itr);
}
}
除了泛型,我们还可以使用特征对象:
fn foo<'a>(itr: &mut Iterator<Item=&'a i32>) {
while let Some(c) = itr.next() {
if *c != 0 {
break;
}
println!("{}", *c);
}
}
fn main() {
let v = vec![0; 10];
let mut itr = v.iter();
while let Some(c) = itr.next() {
foo(&mut itr);
}
}
关于trait objects的章节Rust 书中解释了这些解决方案之间的区别。
关于loops - 如何编写传递给函数的迭代器类型?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36416208/