Rust .next()后面的for。zip():防止移动迭代器
我刚开始生锈,还没有完全弄明白这一切。我一直在读很多书,也在玩数学题。我用这个签名写了一个函数:Rust .next()后面的for。zip():防止移动迭代器,rust,Rust,我刚开始生锈,还没有完全弄明白这一切。我一直在读很多书,也在玩数学题。我用这个签名写了一个函数: pub fn prime_factors(n: u64) -> Vec<u64> { 其中一个亮点是,我正在将静态数组与向量进行比较(出于学习目的,这是当前需要的,因为我想练习泛型) 我的测试功能是我实际遇到问题的功能。要进行测试,函数必须遍历两个集合,检查每个索引是否相等。我使用.zip()来实现这一点,但是如果集合不均匀,迭代器将只遍历较短集合的索引。所以在zip之后,我想检
pub fn prime_factors(n: u64) -> Vec<u64> {
其中一个亮点是,我正在将静态数组与向量进行比较(出于学习目的,这是当前需要的,因为我想练习泛型)
我的测试功能是我实际遇到问题的功能。要进行测试,函数必须遍历两个集合,检查每个索引是否相等。我使用.zip()
来实现这一点,但是如果集合不均匀,迭代器将只遍历较短集合的索引。所以在zip
之后,我想检查迭代器中是否有额外的元素
以下内容未编译:
fn assert_list_eq<I, T>(mut expected: I, mut actual: I)
where I: Iterator<Item=T> + Clone,
T: PartialEq + Debug {
for (e, a) in expected.zip(actual) {
assert_eq!(e, a);
}
// fail if there are any "leftovers"
assert_eq!(None, expected.next());
assert_eq!(None, actual.next());
}
顺便说一句(承认XY问题):我很高兴了解一个内置断言来比较两个有序集合,但这并不是我真正感到困惑的地方。按值获取其参数,因此它们会被移动,以后不能使用它们 但是,有一个解决方法:有一个方法返回对迭代器的可变引用,诀窍是
&muti,其中I:iterator
还实现了迭代器。因此,在将两个迭代器传递到zip()之前,您可以将.by_ref()
应用于这两个迭代器:
[…]
使用trait(。
是RangeFull
的缩写)强制将表达式转换为切片
另一种方法是交换操作数,这样就不需要[…]
#[test]
fn prime_factors_test() {
assert_eq!(prime_factors(30), [2,3,5]);
}
这是因为标准库为Vec提供了impl PartialEq
,但没有为[T;3]
提供impl PartialEq。此外,如果您确实想比较迭代器而不是切片,那么标准库和Itertools中都有。
fn assert_list_eq<I, T>(expected: I, actual: I)
where I: Iterator<Item=T> + Clone,
T: PartialEq + Debug {
assert!(expected.clone().count() == actual.clone().count()); // desperation
for (e, a) in expected.zip(actual) {
assert_eq!(e, a);
}
}
fn assert_list_eq<I, T>(mut expected: I, mut actual: I)
where I: Iterator<Item=T> + Clone,
T: PartialEq + Debug {
for (e, a) in expected.by_ref().zip(actual.by_ref()) {
assert_eq!(e, a);
}
// fail if there are any "leftovers"
assert_eq!(None, expected.next());
assert_eq!(None, actual.next());
}
#[test]
fn prime_factors_test() {
assert_eq!([2,3,5][..], prime_factors(30)[..]);
}
#[test]
fn prime_factors_test() {
assert_eq!(prime_factors(30), [2,3,5]);
}