【问题标题】:Flex default rule弹性默认规则
【发布时间】:2012-05-03 06:47:54
【问题描述】:

如何自定义 flex 的默认操作。我发现了类似 的东西,但是当我运行它时,它显示“flex 扫描仪卡住了”?还有 . rule 只添加一个规则,因此它也不起作用。我想要的是

comment               "/*"[^"*/"]*"*/"

%%
{comment}             return 1;
{default}             return 0; 
<<EOF>>               return -1;

是否可以将匹配最长的行为更改为首先匹配?如果是这样,我会做这样的事情

default               (.|\n)*

但是因为这几乎总是给出更长的匹配,所以它会隐藏评论规则。

编辑

我在手册中找到了 {-} 运算符,但是这个直接来自手册的示例给了我“无法识别的规则”:

[a-c]{-}[b-z]

【问题讨论】:

    标签: c tokenize lex flex-lexer


    【解决方案1】:

    flex 默认规则匹配单个字符并将其打印在标准输出上。如果您不想要该操作,请编写一个匹配单个字符并执行其他操作的显式规则。

    (.|\n)* 模式将整个输入文件作为单个标记匹配,所以这是一个非常糟糕的主意。您认为默认值应该是长匹配,但实际上您希望它尽可能短(但不能为空)。

    默认规则的目的是在输入语言中的任何标记都不匹配时执行某些操作。当 lex 用于标记语言时,这种情况几乎总是错误的,因为这意味着输入以一个字符开头,而该字符不是该语言的任何有效标记的开头。

    因此,“捕捉任何字符”规则被编码为错误恢复的一种形式。这个想法是丢弃坏字符(只有一个)并尝试从那个字符之后的字符进行标记。这只是一个猜测,但这是一个很好的猜测,因为它是基于已知的:即输入中有一个坏字符。

    恢复规则可能是错误的。例如,假设语言中没有任何标记以@ 开头,而程序员想要编写字符串文字"@abc"。只是,她忘记了开头",写了@abc"。正确的解决方法是插入缺少的",而不是丢弃@。但这需要在词法分析器中设置一套更聪明的规则。

    无论如何,通常在丢弃坏字符时,您希望针对这种情况发出错误消息,例如“在第 42 行第 3 列跳过无效字符 '~`”。

    将不匹配字符复制到标准输出的默认规则/操作在使用 lex 进行文本过滤时很有用。然后,默认规则带来了正则表达式搜索的语义(与正则表达式匹配相反):这个想法是在输入中搜索词法分析器的标记识别状态机的匹配项,同时打印该搜索跳过的所有材料。

    例如,一个只包含规则的 lex 规范:

     "foo" { printf("bar"); }
    

    将实现等价于

     sed -e 's/foo/bar/g'
    

    【讨论】:

      【解决方案2】:

      如果尝试匹配规则的补码,我手动解决了问题。这很好用,因为本例中涉及的匹配模式非常简单。

      【讨论】:

      • 解决办法是什么?
      【解决方案3】:

      为什么要加“。”不做的伎俩?如果没有匹配的金额,您将无法执行操作。如果没有匹配,flex 不会做任何事情,所以要添加一个“默认”规则,只需让它匹配一些东西。

      【讨论】:

      • @barfuin 您正在评论一个 11 岁的答案,所以您不妨与另一个人交谈。我同意;随意编辑它。
      猜你喜欢
      • 2016-04-14
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多