rust 带有“.collect()”的for循环无法推断类型

jxct1oxe  于 2023-01-21  发布在  其他
关注(0)|答案(2)|浏览(149)

当运行以下代码时,这些代码来自Rust Book中的练习:

use std::collections::HashMap;

fn main() {
    let mut values = [5, 34, 31, 4, 31, 25, 28, 45, 43, 14];
    values.sort();

    let mut total = 0;
    let mut mode_collection = HashMap::new();
    let mut mode = HashMap::new();

    for value in values.iter() {
        let count = mode_collection.entry(value.clone()).or_insert(0);
        *count += 1;
        total += value;
    };

    for (value, count) in mode_collection.iter() {
        let count_values = mode.entry(count).or_insert(vec![]);
        count_values.push(value.clone());
    }

    let mut largest_count: i32 = 0;
    for count in mode.keys().collect() {
        if count > largest_count {
            largest_count = count;
        }
    }

    println!("The average of the values is {}", total / values.len());
    println!("The median of the values is {}", values[values.len() / 2]);
    println!("The mode of the values is {:?}", mode[&largest_count]);
}

In Rust Playground
我得到一个错误:

error[E0282]: type annotations needed
  --> src\main.rs:24:18
   |
24 |     for count in mode.keys().collect() {
   |                  ^^^^^^^^^^^^^^^^^^^^^ cannot infer type

error: aborting due to previous error

For more information about this error, try `rustc --explain E0282`.
error: could not compile `enums`

To learn more, run the command again with --verbose.

如何避免此错误?
据我所知,类型注解不能添加到for循环中。但是在使用collect()时,类型注解是必需的。当我去掉collect()时,count&&{Integer}(一个双重借用的整数?),所以largest_countcount变量不能比较。

erhoui1w

erhoui1w1#

1.如果你需要一个显式的类型注解,你可以使用下一个语义:

for count in mode.keys().collect::<Vec<_>>() {
   // do stuff over each count
}

1.在for循环中,您不需要收集项来迭代它们。mode.keys()已经是一个迭代器,因此您只需编写:

for count in mode.keys() {
    // do stuff
}

1.如果你需要从迭代器中得到一个结果,最好使用fold

let largest_count = mode.keys().copied().fold(0, |largest, current| largest.max(current));

1.在您的特定情况下,您可以只写:

let largets_count = mode.keys().copied().max();
aij0ehis

aij0ehis2#

您在这里遇到了两个问题:

  1. collect()失败,因为不可能知道生成的集合应该具有什么类型。您可以通过the turbo-fish将该类型注解为mode.keys().collect::<Vec<_>>()。这不会解决您的问题,因为它不会更改正在收集的项的类型。
    1.你可以简单地在循环中解引用整数。这将解决你的问题,并且根本不需要收集。也就是说,**count&&i32转换为i32,并允许你按预期进行比较。
    您可能还需要重新考虑在散列表中存储对整数的引用,然后可以通过对keys()迭代器的copied()调用来解决这个问题。

相关问题