Flex字符串识别“无法识别的规则”错误

时间:2020-06-02 23:26:07

标签: c string bison flex-lexer

我试图创建一个在flex中运行的字符串识别规则,该字符串可以包含转义字符(\ n,\ t,\ r,\,“,'),符号(-,+,*,/, :,_,$,!,#,@,&,〜,^,(,))和a-zA-Z0-9字符,我尝试了以下代码的多种变体,但我不断遇到相同的错误以上。

ESCAPECHAR  [\n] | [\t] | [\r] | [\] | ['] | ["]
SYMBOLS [-+*/:_$!#@&~^()]
CHARACTERS [0-9a-zA-Z]
STRING  ("({ESCAPECHAR} | {SYMBOLS} | {CHARACTERS})*") | ('({ESCAPECHAR} | {SYMBOLS} | {CHARACTERS})*')

1 个答案:

答案 0 :(得分:1)

您最好阅读Flex manual chapter on patterns syntax。它不是很长,并且提供了有关Flex模式语法的完整描述。

以下是您所犯的一些错误:

  1. Flex模式不能包含未加引号的空格(除非您将它们放在带有x标志的子表达式中)。所以

    [\n] | [\t] | [\r] | [\] | ['] | ["]
    

    无效。

  2. 此外,\用于指示:

    • 以下字母是控制字符的代码(因此\n是换行符),或者
    • 以下标点符号不应给予特殊的意义。 因此,在[\]中,\表示后面的]应该被视为普通字符,而不是字符类的结尾,这意味着字符类将继续到下一个]。字符类中的空格字符被认为是带引号的,因此字符类由字符],空格,|['组成。 (Flex允许您在字符类中重复字符,因此它不会抱怨存在两个空格字符。)您可能是指[\\]
  3. 无论如何,您应该以与编写其他字符类相同的方式来编写字符类,即在[]中使用一系列字符或转义代码:

    [\n\t\r\\ '"]
    
  4. Flex使您可以通过用引号将字符引起来来对字符进行引号,以便将“({ESCAPECHAR} | {SYMBOLS} | {CHARACTERS})*”视为单个文字字符串,必须在字面上进行匹配在文本中。您可能希望引号是普通字符,因此您应该将引号转义或将其放入单字符字符类:

    ["]({ESCAPECHAR}|{SYMBOLS}|{CHARACTERS})*["]
    

    同样,有必要从模式中删除空格。

  5. 我假设您的意图是仅在实际上将转义时才允许在字符串中出现“转义字符”。您的{ESCAPECHAR}宏扩展为实际字符的集合,因此它包括换行符,制表符和回车符。它还包括引号和撇号,实际上应该保留它们以终止字符串文字。可能的意思是,如果转义代码前面带有\ (例如C或如上所述的flex本身),则允许它们。在这种情况下,您真正​​需要写的是

    ESCAPECHAR    \\[ntr'"]
    

    (即,\\,其后紧跟字符ntr'" 。)尽管如此,这也不是很精确:它不允许使用\\来表示单个\,并且迫使用户写"Don\'t just copy code."'\"' ,通常都可以在不使用反斜杠转义符的情况下编写两者。

相关问题