【问题标题】:Searching a Vec for a match在 Vec 中搜索匹配项
【发布时间】:2020-06-16 05:06:52
【问题描述】:

我的第一个 Rust 程序编译并运行:

use structopt::StructOpt;
use pcap::{Device,Capture};
use std::process::exit;

#[derive(StructOpt)]
struct Cli {
    /// the capture device
    device: String,
}

fn main() {    
    let devices = Device::list();
    let args = Cli::from_args();

    let mut optdev :Option<Device> = None;
    for d in devices.unwrap() {
        //println!("device: {:?}", d);
        if d.name == args.device {
            optdev = Some(d);
        }
    }

    let dev = match optdev {
        None => {
            println!("Device {} not found.", args.device);
            exit(1);
        },
        Some(dev) => dev,
    };

    let mut cap = Capture::from_device(dev).unwrap()
              .promisc(true)
              .snaplen(100)
              .open().unwrap();

    while let Ok(packet) = cap.next() {
        println!("received packet! {:?}", packet);
    }
}

我有一些复杂的代码遍历设备的 Vec,针对 args.device 测试每个人的 .name 属性。

我猜测有一种方法可以“查找” Vec 中的条目,这样我就可以将所有 optdev 行替换为以下内容:

let dev = match devices.unwrap().look_up(.name == args.device) {
    None => {
        println!("Device {} not found.", args.device);
        exit(1);
    },
    Some(dev) => dev,
};

这样的look_up() 的语法是什么?

或者有更惯用的方法吗?

【问题讨论】:

    标签: vector rust


    【解决方案1】:

    这样的look_up() 的语法是什么?

    Iterator::find。由于该操作不是特定于向量(或切片)的,因此它并不存在于那里,而是适用于任何迭代器。

    看起来像这样:

    let dev = match devices.unwrap().into_iter().find(|d| d.name == args.device) {
        None => {
            println!("Device {} not found.", args.device);
            exit(1);
        },
        Some(dev) => dev,
    };
    

    let dev = if let Some(dev) = devices.unwrap().into_iter().find(|d| d.name == args.device) {
        dev
    } else {
        println!("Device {} not found.", args.device);
        exit(1);
    };
    

    (旁注:您可能还想使用eprintln 来报告错误)。

    虽然更清晰的错误处理可能类似于(注意:未经测试,因此可能存在语义或句法错误):

    use std::fmt;
    use std:errors::Error;
    
    #[derive(Debug)]
    struct NoDevice(String);
    impl fmt::Display for NoDevice {
        fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
            write!(f, "Device {} not found", self.0)
        }
    }
    impl Error for NoDevice {}
    
    fn main() -> Result<(), Box<dyn Error>> {    
        let devices = Device::list()?;
        let args = Cli::from_args();
    
        let dev = devices.into_iter()
                         .find(|d| d.name == args.device)
                         .ok_or_else(|| NoDevice(args.device))?
    
        let mut cap = Capture::from_device(dev)?
                  .promisc(true)
                  .snaplen(100)
                  .open()?;
    
        while let Ok(packet) = cap.next() {
            println!("received packet! {:?}", packet);
        }
    }
    

    【讨论】:

      猜你喜欢
      • 2021-11-16
      • 2013-12-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-03-06
      相关资源
      最近更新 更多