Javacc如何使变量可以被扫描程序和解析器访问

时间:2017-04-14 13:21:38

标签: java javacc

我试图创建一个包含所有函数名称的Map。我可以在扫描阶段或解析阶段执行此操作,但似乎无法获得两者都可访问的相同变量。

我需要的是在开始解析之前将所有函数名称保存在映射中,因为函数可以在其调用的点之下声明。所以我需要检查该功能是否存在。

我尝试过使用令牌mgr声明,这样我就可以在每次看到令牌时将令牌添加到地图中。但是我需要解析器才能看到funcs变量,因此它可以检查函数是否存在。

    TOKEN_MGR_DECLS : {
        public static Map funcs = new HashMap();
    }
    TOKEN : { 
       <FNAME: (["A"-"Z"])+ > { funcs.put(matchedToken.image, "..");}
    }

这是我最接近的,我在.jj文件中尝试了一个全局变量,就在PARSER_BEGIN(..)下面,并在主函数中声明了它。当尝试向地图添加函数名称时,这两个都导致“无法找到符号”错误。

感谢您的帮助。

2 个答案:

答案 0 :(得分:1)

首先我不得不说我建议不要在解析器和词法分析器之间共享任何变量。这是因为词法分析器可以远远超出解析器,这意味着:

  • 如果变量由lexer写入并由解析器读取,则在解析器读取该信息时,该信息可能已过期(即覆盖)。

  • 如果变量由解析器编写并由词法分析器读取,那么当词法分析器需要时,解析器可能不会写入词法分析器所需的信息。

那就是说。如果你需要这样做。这是一种方式。像这样

在令牌管理器中声明你的变量
TOKEN_MGR_DECLS : {
    Map funcs = new HashMap();
}

然后,在解析器中,您可以将变量作为token_source.funcs访问。

如果您使用STATIC=true选项,则该变量应为static

答案 1 :(得分:0)

要想清楚,您想知道javacc解析器的流程。

实际JavaCC进程以解析器部分开始,该部分调用TokenManager通过调用getNextToken()方法返回要处理的令牌。哪个实习生调用字符字符流(SimpleCharStream或JavaCharStream)逐个字符地返回给TokenManager。

   Parser
    /|\
     | getNextToken()
    \|/
TokenManager
    /|\
     | readChar()
    \|/
SimpleCharStream