gpt4 book ai didi

rust - 如何返回盒装迭代器,该盒装迭代器返回f64的盒装迭代器?

转载 作者:行者123 更新时间:2023-12-03 11:30:34 26 4
gpt4 key购买 nike

我正在尝试使用CSV crate读取CSV文件并将其所有单元格懒惰地转换为f64:

use csv::ReaderBuilder; // 1.1.4

fn get_df_iterator(path: &str) {
// Build the CSV reader and iterate over each record casting to f64
let rdr = ReaderBuilder::new()
.delimiter(b'\t')
.from_path(path)
.unwrap();

rdr.into_records().map(|record_result| {
record_result
.unwrap()
.into_iter()
.map(|cell: &str| cell.parse::<f64>().unwrap())
})
}

fn main() {
let m1 = get_df_iterator("df1.csv");
}
playground
我读过要在稳定的Rust中返回带有闭包的类型,我们可以使用 Box es。我已经尝试过:
use csv::{Error, ReaderBuilder, StringRecord};

fn get_df_iterator_box(path: &str) -> Box<dyn Iterator<Item = Box<dyn Iterator<Item = f64>>>> {
// Build the CSV reader and iterate over each record.
let rdr = ReaderBuilder::new()
.delimiter(b'\t')
.from_path(path)
.unwrap();

// Returns Box<Iterator<Item = f64>>
let parse_str = |cell: &str| cell.parse::<f64>().unwrap();

let parse_record = |record_result: Result<StringRecord, Error>| {
Box::new(record_result.unwrap().into_iter().map(parse_str))
};

// Box<Iterator<Item = Box<Iterator<Item = f64>>>>
Box::new(rdr.into_records().map(parse_record))
}

fn main() {
let m1 = get_df_iterator_box("df1.csv");
}
error[E0271]: type mismatch resolving `<[closure@src/main.rs:13:24: 15:6] as FnOnce<(std::result::Result<StringRecord, csv::Error>,)>>::Output == Box<(dyn Iterator<Item = f64> + 'static)>`
--> src/main.rs:18:5
|
11 | let parse_str = |cell: &str| cell.parse::<f64>().unwrap();
| ----------------------------------------- the expected closure
...
18 | Box::new(rdr.into_records().map(parse_record))
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected struct `Map`, found trait object `dyn Iterator`
|
= note: expected struct `Box<Map<StringRecordIter<'_>, [closure@src/main.rs:11:21: 11:62]>>`
found struct `Box<(dyn Iterator<Item = f64> + 'static)>`
= note: required because of the requirements on the impl of `Iterator` for `Map<StringRecordsIntoIter<File>, [closure@src/main.rs:13:24: 15:6]>`
= note: required for the cast to the object type `dyn Iterator<Item = Box<(dyn Iterator<Item = f64> + 'static)>>`
我不明白问题是什么。应该返回一个 Box,其中包含一个迭代器,该迭代器返回 Box的迭代器的 f64Here there's another playground与该更新!如果要复制相同的文件,则使用 here you can download it

最佳答案

您可以指定闭包的返回类型,以告诉Rust您正在返回dyn trait:

let parse_record =
|record_result: Result<StringRecord, Error>| -> Box<dyn Iterator<Item = f64>> {
Box::new(record_result.unwrap().into_iter().map(parse_str))
};
另一种方法是在闭包中显式转换:
let parse_record = |record_result: Result<StringRecord, Error>| {
Box::new(record_result.unwrap().into_iter().map(parse_str)) as Box<dyn Iterator<Item = f64>>
};
您可以改为返回 impl trait 而不是使用动态调度,并完全避免这种情况:
fn get_iterator(path: &str) -> impl Iterator<Item = impl Iterator<Item = f64>> { ... }
有关返回特征的更多信息,请参见 What is the correct way to return an Iterator?

关于rust - 如何返回盒装迭代器,该盒装迭代器返回f64的盒装迭代器?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/65007594/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com