file - 继续从文件中的当前行进行迭代

标签 file rust iteration

我试图弄清楚如何从我当前所在的行继续遍历文件,而不必从头开始。我正在使用BufReader完成逐行迭代。这是我要执行的操作的一个示例:

use std::{
    fs::File,
    io::{self, BufRead, BufReader},
};

fn main() -> io::Result<()> {
    let chapter = "Chapter 1";
    let sentence = "Sentence 1";

    let file = File::open("document.txt")?;
    let reader = BufReader::new(file);

    for line in reader.lines() {
        if chapter == line.unwrap() {
            for line in reader.lines() {
                if sentence == line.unwrap() {
                    println!("Found the reference!");
                }
            }
        }
    }

    Ok(())
}
由于错误,我无法像这样迭代:
error[E0382]: use of moved value: `reader`
    --> src/main.rs:15:25
     |
11   |     let reader = BufReader::new(file);
     |         ------ move occurs because `reader` has type `std::io::BufReader<std::fs::File>`, which does not implement the `Copy` trait
12   | 
13   |     for line in reader.lines() {
     |                        ------- `reader` moved due to this method call
14   |         if chapter == line.unwrap() {
15   |             for line in reader.lines() {
     |                         ^^^^^^ value moved here, in previous iteration of loop
     |
note: this function consumes the receiver `self` by taking ownership of it, which moves `reader`
有没有办法使用相同的BufReader继续进行行迭代?

最佳答案

我认为在所有情况下都必须对迭代进行解糖,因为与内置for所允许的相比,您需要更多的控制权。我在这里看到两种可能性:
一种,只需将糖简化为while let并在两个循环中使用相同的迭代器:

while let Some(line) = lines.next() {
    if chapter == line.unwrap() {
        while let Some(line) = lines.next() {
              if sentence == line.unwrap() {
                     println!("Found the reference!");
              }
        }
    }
}
这意味着“内部”循环将从“外部”循环停止的地方开始,但是“外部”循环将从“内部”停止的地方继续。
如果这是不希望的,则可以使用 Itertools::tee “ fork ”迭代器,但是我希望这需要将迭代器装箱,因为您要堆叠Tee。这意味着要累积一堆动态调度的迭代器。tee还要求Item是可克隆的(另一项费用),这意味着您必须在迭代之前拆开值:
let mut lines: Box<dyn Iterator<Item=_>> = Box::new(BufReader::new(file).lines().map(|l| l.unwrap()));

while let Some(line) = lines.next() {
    let (a, sub) = lines.tee();
    lines = Box::new(a);
    if chapter == line {
        for line in sub {
              if sentence == line {
                     println!("Found the reference!");
              }
        }
    }
}

关于file - 继续从文件中的当前行进行迭代,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/64852996/

相关文章:

rust - 如何检查用户输入的变量是数字(int,float)?

python - 找到 N 个组中 N 个项目的所有组合,而没有重复的项目组合(python)?

java - 如何检查字符串是否包含列表中的子字符串?

java - 在reducer中迭代读取hadoop reducer输出

android - new File() 给出 IllegalArgumentException : File contains a path separator

multithreading - 如何将对堆栈变量的引用传递给线程?

file - augeas 的示例文件

rust - 一个别名可以在 rust 中绑定(bind)更高等级的特征吗?

c - 从文件写入/读取结构中的结构

c - 用C读取二进制文件