【发布时间】:2019-10-05 04:18:46
【问题描述】:
为什么__LINE__ 的计算结果会根据它是在类函数宏还是常规函数中使用而有所不同?
例如:
#include<stdio.h>
#define A() printf("%d\n",__LINE__);
int main(void) {
/* 6 */ A();
/* 7 */ A(
/* 8 */ );
/* 9 */ printf("%d\n",__LINE__
/* 10 */ );
}
我希望得到:
6
7
9
但是我们得到(使用 clang-1000.10.44.4):
6
8
9
注意在第 7 行和第 8 行的类函数宏中,使用的是最后一行,而不是第一行。
GCC 的文档很详细:https://gcc.gnu.org/onlinedocs/cpp/Standard-Predefined-Macros.html
我为什么要关心?我正在编写一个解析器,它需要查找宏 A 的所有实例的行号,以便与 __LINE__ 将返回的内容对齐。由于需要解析可能转义的参数,因此要找到宏用法的 last 行而不是 first 行要困难得多。
【问题讨论】:
-
最终你还是需要正确地进行解析,因为宏参数中可能存在宏以及其他复杂情况。
-
我很惊讶地看到,输出随着上一个 gcc 版本而改变。所以:不用担心。当您更新到 gcc9.1 时,输出将匹配预期(!),请参阅 godbolt。当使用
gcc -E时,我也很惊讶地看到main的第二行末尾没有双;;。 -
@Kamil: 失踪的
;是来自godbolt 的礼物。如果您禁用过滤“仅评论行”(//按钮),您将在两个 gcc 版本上看到分号。 -
@KamilCuk #1 godbolt 太棒了,#2 我很害怕这种行为在 gcc 9 中发生了变化。这足以让我重新考虑我的日志记录方法。
标签: c gcc c-preprocessor