【问题标题】:Multi-line comments and new-lines多行注释和换行
【发布时间】:2013-03-04 22:42:12
【问题描述】:

在 C++11 中,标准在 2.2.3 中说:

每条评论都被一个空格字符替换。保留换行符。

  1. 这个短语是连续的,意思是保留换行符以换行符结尾的注释吗?

  2. 如果 (1) 为真,那么为什么 Visual C++、gcc 和 clang 在多注释中为每一行保留空行。

这个问题很重要,因为我正在编写一个 c++ 预处理器。

【问题讨论】:

  • 顺便说一下,这对宏声明特别有意义,因为它们以(非拼接)new-line 字符结尾。
  • @K-ballo:即使多行注释在#define 之后开始并在 10 行之后结束,然后是 macro_name 及其定义,它仍然可以工作并且宏将有效

标签: c++ c++11 c-preprocessor


【解决方案1】:

它所说的新行是在 cmets 被单个空格字符替换后仍然存在的行。当在包含它的段落的更大上下文中查看 sn-p 时,这一点会更清楚。

所以特别是多行 cmets 中的新行保留,并且不终止预处理指令。

【讨论】:

  • 如果这是真的,那么你对问题 2 的回答是什么?
  • @Muhammadalaa:他们并没有按照标准的含义保留它。正在发生的事情是,为了很好地打印预处理器的输出,而不是将所有非换行空格与单个空格相同,它们将其中的一些保留在“空格标记”中。但是从逻辑上讲,这对预处理器的功能没有影响,只是这样做是为了使gcc -E 的中间输出更易于阅读。
【解决方案2】:

C/C++ 预处理器会去除所有 cmets,但在查看预处理器输出时通常会将源代码行保持在相同的行号。

这是为了让读取预处理器输出的编译器可以为错误消息和警告打印正确的行号。

预处理器通常也会保留所有空行。

您还必须严格区分从源中删除的多行宏和扩展它们的时间。它们总是被删除同时保留所有换行符。它们总是被替换为所有换行符被删除。两者都是完全独立的操作,彼此无关。

在过去,C 预处理器总是在标准输出上产生其输出,而 C 编译器会从标准输入中读取它。预处理器发出内部#<N> "<FILE>" 语句,C 编译器将其解释为“行号 N 跟随”。所以理论上预处理器可以在输出中不产生空行。但在实践中,这个#<N> "<FILE>" 功能仅用于#include 语句之后的行。

如今,为了提高性能,C 编译器中内置了预处理器,但如果明确要求,您仍然可以查看中间结果。

注意:另请参阅下面的好评论:该标准并未真正指定预处理器的文本输出在空格方面的外观。文本输出是特定于实现的。有很大的解释空间。所定义的是必须至少有一个空格字符,并且所有标记都保留在其原始行上(或使用其原始行进行标记),以便错误消息有意义。

【讨论】:

  • 好帖子,但区分标准指定的内容和特定于实现的内容很重要。阶段 4 的标准逻辑输出是 preprocessing-tokens 的序列,没有明显的空白。您描述的“文本”输出格式(例如来自gcc -E)不是标准要求或指定的。一个符合标准的预处理器不需要产生这种格式,即使它产生了,它也没有很好地指定到预处理器之间的差异等效。在成功理解第 16 条之前,需要先理解这一点。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-09-29
  • 2010-10-13
  • 2014-01-15
  • 2017-08-07
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多