C 可变宏:相同代码的不同输出

C 可变宏:相同代码的不同输出,c,gcc,undefined-behavior,preprocessor,C,Gcc,Undefined Behavior,Preprocessor,我在CLion做了一个项目来测试macroes。 我创建了一个宏来计算给定给它的参数数量。 首先,这个宏给了我有效的输出(0表示没有参数,1表示一个参数,2表示两个参数…)。 但是,我不知道发生了什么,我的宏不知怎么就失效了。可能是由于很多SIG_ILL故障,当我从函数的声明范围外调用函数时,未定义的行为,我在表达式内声明了函数 我试图实现方法和新< /Cord>操作符,如C++,但通过C预处理器,它最终成功,直到我的宏计数计数失败。 它现在给出1表示无参数,1表示一个参数,2表示两个参数。这个

我在CLion做了一个项目来测试macroes。 我创建了一个宏来计算给定给它的参数数量。 首先,这个宏给了我有效的输出(0表示没有参数,1表示一个参数,2表示两个参数…)。 但是,我不知道发生了什么,我的宏不知怎么就失效了。可能是由于很多SIG_ILL故障,当我从函数的声明范围外调用函数时,未定义的行为,我在表达式内声明了函数

我试图实现方法和<代码>新< /Cord>操作符,如C++,但通过C预处理器,它最终成功,直到我的宏计数计数失败。 它现在给出1表示无参数,1表示一个参数,2表示两个参数。这个错误发生在编译时,而CLion的特性“inline current usage”告诉我,当在没有参数的情况下调用该宏时,该宏应该扩展到0

这是这个项目,只是简单的main.c:

#include <stdio.h>

#define Macro_argument_20(_1, _2, _3, _4, _5, _6, _7, _8, _9, _10, \
_11, _12, _13, _14, _15, _16, _17, _18, _19, _20, ...) _20

#define Macro_argumentsAmount(ARGS...) \
Macro_argument_20("dummy", ##ARGS, 18, 17, 16, 15, 14, 13, 12, 11,10,\
9, 8, 7, 6, 5, 4, 3, 2, 1, 0)

int main() {
    printf("%i", Macro_argumentsAmount());

    return 0;
}
我在两个项目中都看到了以下主要内容(尽管其中一个打印了0):


-std=c17
选项添加到编译器时,将禁用
##ARGS
的GCC逗号吞咽扩展


使用
-std=gnu17
来启用与c2017功能一起使用的GNU扩展。

请不要发布屏幕截图。发布一个显示问题的帖子,以便人们可以复制、粘贴、编译、运行。很抱歉,我找不到隐藏图像的选项。这个问题看起来不可思议,所以我想给出证明。
Macro\u argumentsAmount()
0个参数还是一个空参数?你为什么期望一个胜过另一个?对于
Macro\u argumentsAmount(,)
,您希望得到什么结果?@Chris,
Macro\u argumentsAmount()
必须扩展到0,这就是当
ARGS
在这样的上下文中导致空参数时#运算符的工作方式。对于
宏\u argumentsAmount(,)
,这应该是2,因为您显式地将空参数转发给宏,它只会扩展为一个coma,这意味着在它的两侧都有两个参数。空参数也是一个参数。我本可以通过对每一个论点进行严格的分析并询问它的长度来检查这个问题,但是这样的一个观点对我来说太荒谬了,没有必要。你说的“纯C”是什么意思<代码>##ARGS是一个非标准的gcc扩展,这段代码不会用严格的C编译器编译。哦,我刚刚注意到,在使用cmake编译器选项时,非常感谢,这是非常意外的
gcc -E main.c -std=c17  -fplan9-extensions  -Werror -Wno-implicit - 
Wno-error=variadic-macros -Wno-error=implicit-fallthrough
# 9 "main.c"
int main() {
 printf("%i", 1);

 return 0;
}