本文共 2704 字,大约阅读时间需要 9 分钟。
在GNU C中,宏可以接受可变数目的参数,就象函数一样,例如:
1 2 |
|
用可变参数宏(variadic macros)传递可变参数表
你可能很熟悉在函数中使用可变参数表,如: 1 |
|
直到最近,可变参数表还是只能应用在真正的函数中,不能使用在宏中。
C99编译器标准终于改变了这种局面,它允许你可以定义可变参数宏(variadic macros),这样你就可以使用拥有可以变化的参数表的宏。可变参数宏就像下面这个样子:
1 |
|
缺省号代表一个可以变化的参数表。使用保留名 __VA_ARGS__ 把参数传递给宏。当宏的调用展开时,实际的参数就传递给 printf()了。例如:
1 |
|
1 |
|
1 |
|
用GCC和C99的可变参数宏, 更方便地打印调试信息
gcc的预处理提供的可变参数宏定义真是好用:
1 2 3 4 5 6 |
|
如此定义之后,代码中就可以用dbgprint了,例如dbgprint("%s", __FILE__);
下面是C99的方法:
1 |
|
新的C99规范支持了可变参数的宏
具体使用如下:以下内容为程序代码:
1 2 3 4 5 6 7 8 |
|
但现在似乎只有gcc才支持。
可变参数的宏里的'##'操作说明带有可变参数的宏(Macros with a Variable Number of Arguments) 在1999年版本的ISO C 标准中,宏可以象函数一样,定义时可以带有可变参数。宏的语法和函数的语法类似。下面有个例子: 1 |
|
1 |
|
为了解决这个问题,CPP使用一个特殊的'##'操作。书写格式为:
1 |
|
这里,如果可变参数被忽略或为空,'##'操作将使预处理器(preprocessor)去除掉它前面的那个逗号。如果你在宏调用时,确实提供了一些可变参数,GNU CPP也会工作正常,它会把这些可变参数放到逗号的后面。象其它的pasted macro参数一样,这些参数不是宏的扩展。
##还可以起到替换作用 如: 1 |
|
怎样写参数个数可变的宏
一种流行的技巧是用一个单独的用括弧括起来的的 ``参数" 定义和调用宏, 参数在 宏扩展的时候成为类似 printf() 那样的函数的整个参数列表。 1 2 |
|
1 2 3 |
|
C99 引入了对参数个数可变的函数式宏的正式支持。在宏 ``原型" 的末尾加上符号 ... (就像在参数可变的函数定义中), 宏定义中的伪宏 __VA_ARGS__ 就会在调用是 替换成可变参数。
最后, 你总是可以使用真实的函数, 接受明确定义的可变参数如果你需要替换宏, 使用一个 函数和一个非函数式宏, 如 #define printf myprintf
转载地址:https://linus.blog.csdn.net/article/details/82948566 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!