0

我正在考虑将 CUP 解析器生成器用于项目。为了正确解析我将要编译的语言的一些结构,我需要词法分析器(由 JFlex 生成)来使用符号表中的信息(不是解析表——我的意思是我将存储的表有关标识符的信息),以便在调用其 next_token() 方法时生成正确的令牌类型。由于符号表中的信息静态依赖于程序文本,因此只有在使用解析器“同步”调用 next_token() 方法时才会起作用。换句话说,如果解析器在需要另一个标记时调用词法分析器,这将起作用,但如果(例如)有一个并行线程正在调用词法分析器并缓冲队列中的标记,则不会。

因此问题是:CUP 如何调用词法分析器?它是否在需要下一个令牌时调用它?我当然可以只编写一个 CUP 语法规范并检查生成的解析器的源文件以查看发生了什么,但这可能比必要的工作更多。我在相关网站上找不到这方面的任何信息。

非常感谢您提供的任何帮助!

4

3 回答 3

2

不久前我完成了解析器和扫描器的实现。这是我发现的:

CUP 确实会在需要时调用扫描仪。它总是在到目前为止已识别的内容之前再缓冲一个标记(前瞻标记)。提前没有花哨的令牌缓冲。

话虽如此,在解析期间设置词法分析器状态可能会很棘手,因为这会导致许多语法冲突。我想这与 CUP 表示嵌入在产品中的语义动作的方式有关。尽管如此,这迫使我放弃了最初的设计,但这并不是我害怕的原因。

希望这对某人有帮助!

于 2015-02-20T16:15:59.430 回答
1

也许这个回复对您来说可能为时已晚,但它可能对其他用户有用。首先要知道的是,如果没有扫描器,解析器将无法做任何事情。事实上,解析器的构造函数的第一个参数就是扫描器。编译 .cup 文件后,您将得到一个与 .cup 同名的 .java 文件作为输出。假设它的名字是 Parser。因此,在项目的主类中,您必须添加以下行:

TmpParser p = new TmpParser (new Scanner (new Reader (s)));   
        p.parse();

您应该将此代码发布到 try-catch 块中。使用 parse 方法,Parser 开始执行操作,并调用 Scanner 的 next_token 方法,以识别令牌并验证您编写的语法规则是否正确。

于 2015-01-21T19:38:53.330 回答
0

我不知道我回答这个问题有多晚,但我正在构建 1 个解析器作为我课程工作的一部分。我分别将 Lex 和 CUP 用于 lexer 和 Parser。我还包括我的主类,它调用解析器,它在获取令牌调用需要时进行扫描所以我的驱动程序类将是:

// construct the lexer, 
Yylex lexer = new Yylex(new FileReader(filename));
// create the parser
Parser parser = new Parser(lexer);
// and parse

解析器实习生调用:

Parser.parse() {
    ...
    this.cur_token = this.scan();
    ...
}

public Symbol scan() throws Exception {
    Symbol sym = this.getScanner().next_token();
    return sym != null ? sym : this.getSymbolFactory().newSymbol("END_OF_FILE", this.EOF_sym());
}

parser.parse();
于 2016-10-09T17:49:14.593 回答