首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >如何在Rust中读取和处理管道分隔的文件?

如何在Rust中读取和处理管道分隔的文件?
EN

Stack Overflow用户
提问于 2017-05-10 09:00:44
回答 2查看 1.6K关注 0票数 0

我希望读取管道分隔的文件,处理数据,并生成CSV格式的结果。

输入文件数据

代码语言:javascript
运行
复制
A|1|Pass
B|2|Fail
A|3|Fail
C|6|Pass
A|8|Pass
B|10|Fail
C|25|Pass
A|12|Fail
C|26|Pass
C|26|Fail

我想按函数在第1列和第3列上应用一个组,并根据特定的组生成列2的和。

在如何维护记录以按功能应用组的问题上,我陷入了困境:

代码语言:javascript
运行
复制
use std::fs::File;
use std::io::{BufReader};
use std::io::{BufRead};
use std::collections::HashMap;

fn say_hello(id: &str, value: i32, no_change : i32) {

    if no_change == 101 {
        let mut data = HashMap::new();
    }
    if value == 0 {
        if data.contains_key(id) {
            for (key, value) in &data {
                if value.is_empty() {

                }
            }
        } else {
            data.insert(id,"");
        }
    } else if value == 2 {
        if data.contains_key(id) {
            for (key, value) in &data {
                if value.is_empty() {

                } else {

                }
            }
        } else {
            data.insert(id,"");
        }
    }
}

fn main() {

    let f = File::open("sample2.txt").expect("Unable to open file");
    let br = BufReader::new(f);
    let mut no_change = 101;
    for line in br.lines() {
        let mut index = 0;
        for value in line.unwrap().split('|') {
            say_hello(&value,index,no_change);
            index = index + 1;
        }
    }
}

我期待着这样的结果:

代码语言:javascript
运行
复制
name,result,num
A,Fail,15
A,Pass,9
B,Fail,12
C,Fail,26
C,Pass,57

是否有任何特定的技术来读取管道分隔的文件并像上面那样处理数据?Python的熊猫完成了这个要求,但我想在Rust中完成。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2017-05-10 21:57:39

如前所述,使用csv箱来完成解析文件的繁重工作。然后,只需使用BTreeMap对每一行进行分组,这也有助于执行排序。入口API帮助高效地插入到BTreeMap中。

代码语言:javascript
运行
复制
extern crate csv;
extern crate rustc_serialize;

use std::fs::File;
use std::collections::BTreeMap;

#[derive(Debug, RustcDecodable)]
struct Record {
    name: String,
    value: i32,
    passed: String,
}

fn main() {
    let file = File::open("input").expect("Couldn't open input");
    let mut csv_file = csv::Reader::from_reader(file).delimiter(b'|').has_headers(false);

    let mut sums = BTreeMap::new();
    for record in csv_file.decode() {
        let record: Record = record.expect("Could not parse input file");
        let key = (record.name, record.passed);
        *sums.entry(key).or_insert(0) += record.value;
    }

    println!("name,result,num");
    for ((name, passed), sum) in sums {
        println!("{},{},{}", name, passed, sum);
    }
}

您将注意到输出是正确的:

代码语言:javascript
运行
复制
name,result,num
A,Fail,15
A,Pass,9
B,Fail,12
C,Fail,26
C,Pass,57
票数 2
EN

Stack Overflow用户

发布于 2017-05-10 10:50:24

我建议你这样做:

代码语言:javascript
运行
复制
use std::str;
use std::collections::HashMap;
use std::io::{BufReader, BufRead, Cursor};

fn main() {
    let data = "
A|1|Pass
B|2|Fail
A|3|Fail
C|6|Pass
A|8|Pass
B|10|Fail
C|25|Pass
A|12|Fail
C|26|Pass
C|26|Fail";
    let lines = BufReader::new(Cursor::new(data))
        .lines()
        .flat_map(Result::ok)
        .flat_map(parse_line);
    for ((fa, fb), s) in group(lines) {
        println!("{}|{}|{}", fa, fb, s);
    }
}

type ParsedLine = ((String, String), usize);

fn parse_line(line: String) -> Option<ParsedLine> {
    let mut fields = line
        .split('|')
        .map(str::trim);
    if let (Some(fa), Some(fb), Some(fc)) = (fields.next(), fields.next(), fields.next()) {
        fb.parse()
            .ok()
            .map(|v| ((fa.to_string(), fc.to_string()), v))
    } else {
        None
    }
}

fn group<I>(input: I) -> Vec<ParsedLine> where I: Iterator<Item = ParsedLine> {
    let mut table = HashMap::new();
    for (k, v) in input {
        let mut sum = table.entry(k).or_insert(0);
        *sum += v;
    }
    let mut output: Vec<_> = table
        .into_iter()
        .collect();
    output.sort_by(|a, b| a.0.cmp(&b.0));
    output
}

操场链接

在这里,HashMap用于对条目进行分组,然后将结果移动到Vec进行排序。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/43887908

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档