是否可以在同一个匹配臂中组合两种模式,一种带有匹配防护装置?

use*_*932 12 rust

我想检查字符串是否包含'$'以及'$'后面是否有内容:

我试过这段代码:

fn test(s: String) {
    match s.find('$') {
        None | (Some(pos) if pos == s.len() - 1) => {
          expr1();
        }
        _ => { expr2(); }
    }
}
Run Code Online (Sandbox Code Playgroud)

但它没有编译:

error: expected one of `)` or `,`, found `if`
Run Code Online (Sandbox Code Playgroud)

它是不可能的结合NoneSome比赛时手臂?

如果是这样,expr1()除非将其移动到单独的函数中,否则有一种简单的方法可以不复制?

Luk*_*odt 7

将匹配保护(thingy)仅适用于一种模式替代(用符号分隔的东西)是不可能的.每只手臂只有一个防护装置,它适用于该手臂的所有模式.if|

但是,有许多解决方案可以解决您的具体问题.例如:

if s.find('$').map(|i| i != s.len() - 1).unwrap_or(false) {
    expr2();
} else {
    expr1();
}
Run Code Online (Sandbox Code Playgroud)

  • 这有效,但依赖于`$`是ASCII并因此占用一个字节的事实.更通用的解决方案可能使用[`char :: len_utf8`](https://doc.rust-lang.org/std/primitive.char.html#method.len_utf8):`i!= s.len() - "c'.len_utf8()`. (3认同)
  • 我想要代码高尔夫:`s.chars().skip_while(| i | i!='$').skip(1).next().is_some()`比任何索引计算都要清晰得多 (2认同)