在编译器中对AST结构进行模式匹配

时间:2015-06-03 15:23:04

标签: pattern-matching rust

所以我试图在结构上进行模式匹配。这个特殊的结构由许多枚举构成,这些枚举包含指向枚举的指针,或者在最基本的层次上,是一个未签名的8字节向量。我想使用矢量,但是想知道是否可以将模式匹配到vec。

ast::ExprUnary(ast::UnDeref, ref exprs) =>{
        let pat = match exprs.node {

            ast::ExprLit(ast::Lit(codemap::Spanned(ast::LitBinary(string),innerspan))) => {
                 //stuff to string
                 //primary issue here is that these enums, which ExprLit is 
                 //comprised of, do not pattern match correctly
            }
            _ => //other stuff
        };

编译此代码后,我收到以下两个错误,

unresolved enum variant, struct or const `Spanned`
unresolved enum variant, struct or const `Lit`

这两个枚举都存在于ast中,但是,我不知道为什么它们在这个特定的上下文中没有得到解决。任何建议将不胜感激

2 个答案:

答案 0 :(得分:7)

有些事情在这里出错了。

  1. ast::Lit只是codemap::Spanned的类型别名,而不是枚举或枚举变体。因此,您不需要同时指定两者,但必须指定。
  2. ast::ExprLit是一个包含P<Lit>的枚举变体。因此,您需要使用PP(inner)进行解构
    • 至少我记得做P - 以这种方式解构。文档说不然。如果它不起作用,您需要取消引用它并为内容添加另一个内部匹配
  3. codemap::Spanned是一个结构,而不是一个元组结构,这意味着你不能按位置匹配它的字段,但你必须按名称对字段进行结构化,如下所示:

    let codemap::Spanned {
        node: innernode,
        span: innerspan,
    } = some_spanned;
    
  4. 总的来说,我相信你的比赛应该看起来像

    let pat = match exprs.node {
        ast::ExprLit( P( codemap::Spanned {
            node: ast::LitBinary(string),
            span: innerspan,
        })) => {
            //stuff to string
            //primary issue here is that these enums, which ExprLit is 
            //comprised of, do not pattern match correctly
        }
        _ => { //other stuff }
    };
    

答案 1 :(得分:0)

我曾经写过这样的代码,但它很烦人。现在我只是use syntax::ast::*并且不在代码中的所有ast::。这也将处理Lit(因为它在syntax::ast

我无法确定实际问题是什么,因为您的代码不完整,但请查看https://github.com/Manishearth/rust-clippy/blob/master/src/len_zero.rs以获取成功的编译示例。