【问题标题】:Skipping nested comments recursively in a scanner在扫描仪中递归地跳过嵌套注释
【发布时间】:2021-11-05 03:52:28
【问题描述】:

我正在为编译器编写扫描程序,并且有一个功能可以在看到 cmets 时跳过它们,我想知道如何以递归方式跳过嵌套的 cmets,即“hello”w“world”之类的东西,到目前为止我有类似的东西:

while ( current_char != '#' ){ // comments in this language starts with $# and end with #$)
      next_char(); // gets the next character in our file

}

【问题讨论】:

  • " hello "w" world" 是如何嵌套评论的?
  • 请注意,在 C 中,没有嵌套的 cmets。 /* This is /* not a nested */ comment */ 不是嵌套评论。这是一条注释,后面跟着一个语法错误。
  • 这不是一个简单的练习,因此匹配引号也是必不可少的(并且“转义”引号是字符串的一部分,而不是分隔符),因为字符串中的注释标记可能不是实际的 cmets .维护一堆嵌套。
  • 简单的解决方案:识别/**/并维护一个计数器。其他解决方案:递归下降,或显式堆栈(状态)
  • 另外,在实际手动编写扫描仪/解析器之前,请查看flexbison。计算机语言解析在很大程度上是一个已解决的问题。

标签: c recursion compiler-construction lexical-analysis


【解决方案1】:

使用深度计数器的嵌套 cmets

最简单的方法是维护一个“评论深度”的计数器:

  • 每次遇到$#,递增计数器;
  • 每次遇到#$,递减计数器。

当计数器为 0 时,您正在阅读代码;当计数器为 1 或更多时,您正在阅读评论。

阅读评论时,忽略除$##$ 之外的所有内容。

例子:

Code $# comment depth 1 $# comment depth 2 #$
comment depth 1 #$ code $# comment depth 1 #$ code

字符串中的转义字符

您提到了以下示例:

" hello "w" world"

让我强调以下建议:

如果开始注释和结束注释符号相同,则不允许嵌套 cmets。

否则,将无法区分以下两种情况:

Situation 1:  "comment" code "comment"
Situation 2:  "comment "nested comment" comment"

请注意,符号" 通常用于字符串,而不是 cmets。没有“嵌套字符串”之类的东西(这意味着什么??)。但是,存在“字符串中的转义字符”之类的东西。实际上,如果您希望字符串包含字符 " 怎么办?通常的做法是保留一个转义字符;直接跟在转义字符之后的字符不会被解释。因此,您可以编写以下字符串:

" hello \"w\" world"

令人满意的是,您可以注意到 StackOverflow 的自动语法着色正确地将所有字符串着色为绿色;而没有\ 的前一个字符串没有正确着色。

【讨论】:

    猜你喜欢
    • 2014-10-26
    • 2013-05-14
    • 2013-01-31
    • 1970-01-01
    • 2023-03-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多