Flex如何区分A,AB和ABC?

时间:2017-02-09 18:56:54

标签: parsing flex-lexer

我为Flex做了这个实验,看看我是否输入ABC,是否会看到所有A,AB,ABC或只有ABC,或只是表达列表中的第一个匹配。

%{
#include <stdio.h>
%}

%%
A puts("got A");
AB puts("got AB");
ABC puts("got ABC");
%%

int main(int argc, char **argv)
{
    yylex();

    return 0;
}

当我在编译并运行程序后进入ABC时,它会响应&#34;获得ABC&#34;这真让我感到惊讶,因为我认为lex并没有跟踪访问过的文本,只发现了第一场比赛;但实际上,它似乎找到了最长的匹配。

当且仅当不再匹配时,Flex使用什么策略来响应A?

1 个答案:

答案 0 :(得分:3)

(F)lex使用maximal-munch原则这一事实应该不足为奇,因为Flex manual中有详细记载:

  

当生成的扫描程序运行时,它会分析其输入,查找与其任何模式匹配的字符串。如果它找到多个匹配项,则需要匹配最多文本的那个...如果找到两个或多个相同长度的匹配项,则会选择Flex输入文件中第一个列出的规则。   (“输入如何匹配”一节的第一段)

精确的算法非常简单:每次请求令牌时,flex都会扫描文本,在DFA中移动。每次遇到接受状态时,它都会记录当前的文本位置。当不再有可能的转换时,它将返回到最后记录的接受位置,并且它将成为令牌的结束。

结果是(F)lex可以多次扫描相同的文本,尽管它只扫描每个令牌一次。

一组需要过多反向跟踪的词法规则会减慢词法扫描速度。这将在Flex手册部分Performance Considerations中讨论,并提供一些避免此问题的策略。但是,除病理情况外,反向跟踪的开销并不明显。