if-let语句的语法是什么?

时间:2017-10-27 18:13:18

标签: syntax rust

我在一些示例代码中遇到了这个代码段。它工作正常,但我得到一个linter错误,说它应该被构造为if-let语句。

match event {
  glutin::Event::WindowEvent { event, .. } => match event {
      glutin::WindowEvent::Closed => return glutin::ControlFlow::Break,
      glutin::WindowEvent::Resized(w, h) => gl_window.resize(w, h),
      _ => (),
  },
  _ => ()
}

这是我尝试对其进行重组:

if let _ = glutin::Event::WindowEvent { event, .. } {
    match event {
       glutin::WindowEvent::Closed => return glutin::ControlFlow::Break,
       glutin::WindowEvent::Resized(w, h) => gl_window.resize(w, h),
       _ => (),
   }
}

哎呀,这是一个语法错误。清除催眠警告的正确方法是什么?

在仔细查看代码之后,我意识到我不理解语法。 glutin::Event::WindowEvent { event, .. }看起来像是创建WindowEvent的新实例的语法,但是如何在匹配语句中允许这样做?

此外,..是什么意思?我熟悉..Default::default(),但不熟悉双点。

2 个答案:

答案 0 :(得分:2)

躲过你的语法称为destructuring

此模式允许匹配struct,enum或tuple中的某些字段。因此,您不能只使用绑定右侧的解构。

您想要的代码可能是:

if let glutin::Event::WindowEvent { event, .. } = event {
  match event {
      glutin::WindowEvent::Closed => return glutin::ControlFlow::Break,
      glutin::WindowEvent::Resized(w, h) => gl_window.resize(w, h),
      _ => (),
  }
}

右手event变量与从模式中提取的变量之间可能存在混淆。 在解构中使用event是强制性的,因为它需要按名称使用struct字段。

答案 1 :(得分:2)

直接引用The Book, second edition

  

if let语法允许您将iflet组合成一种不那么冗长的方式来处理与一种模式匹配的值,而忽略其余模式。

它也提供了这个例子:

if let Some(3) = some_u8_value {
    println!("three");
}

正确的语法是if let «pattern» = «expression» { ... },而不是问题中写的相反。

if let glutin::Event::WindowEvent { event, .. } = event {
    // ...
}