什么类型的内容可以用作C预处理器宏的参数?

什么类型的内容可以用作C预处理器宏的参数?,c,c-preprocessor,C,C Preprocessor,老实说,我很了解C编程语言的语法,但对C预处理器的语法几乎一无所知,尽管我有时会在编程实践中使用它 所以问题来了。假设我们有一个简单的宏,它扩展为零: #define macro(param) 宏调用构造中的语法限制是什么 调用宏时,当然不可能使用单个或多个逗号: macro(,); // won't compile macro("); // compile error 但是,如果我们将逗号放在括号中,它将被C预处理器接受: macro((,)); // compiles fine 当然

老实说,我很了解C编程语言的语法,但对C预处理器的语法几乎一无所知,尽管我有时会在编程实践中使用它

所以问题来了。假设我们有一个简单的宏,它扩展为零:

#define macro(param)
宏调用构造中的语法限制是什么

调用宏时,当然不可能使用单个或多个逗号:

macro(,); // won't compile
macro("); // compile error
但是,如果我们将逗号放在括号中,它将被C预处理器接受:

macro((,)); // compiles fine
当然,您不能使用注释字符:

macro(//); // compile error
因为,据我所知,注释是由预处理器本身处理的

使用宏时,不允许使用未闭合的引号和圆括号:

macro(,); // won't compile
macro("); // compile error
但C语法中未使用的字符是可以接受的:

macro(@#$); // compiles
即使是外语的字符也能很好地工作:

macro(бла-бла-бла я пишу по-русски); // compiles too
调用宏时,是否可以使用花括号中的随机有效C/C++代码?我可以使用没有花括号的随机有效C/C++代码吗?以下代码似乎编译得很好:

macro(int a = 5; printf("%d\n", a););

您不能传递任意文本,以便在建议的方案中忽略:

  • C预处理器将读取输入文件,并在剥离注释后将其作为一系列预处理标记进行解析,以作为参数传递给宏。它匹配括号以确定哪些标记构成由
    分隔的参数

  • 包含具有无法识别的转义序列或独立反斜杠的字符串或字符常量的文本不会作为标准预处理标记进行分析。是否
    宏(@#$)编译依赖于实现

  • 但是请注意,您可以通过将宏定义为具有可变数量的参数来解决
    问题:

    #define macro(...)
    

您需要阅读标准文档,其中将详细解释。如果您只是想学习,如果您试图滥用预处理器,那么请接受以下建议:不要!。请注意,例如,使用预处理器跨越多行代码会使调试非常困难,因为它会将整个代码块扩展到一行。因此,调试器会将同一行中的任何错误报告到代码块中,该代码块可以是多行(逻辑行、可视行、以分号分隔的段)。@IharobAlAsimi:C标准不包括C预处理器。@MarkBenningfield真的吗?让我确认一下。@MarkBenningfield您错了,C标准覆盖了宏。@MarkBenningfield。在预处理器开始工作之前,注释被删除(视为空格)。