【发布时间】:2012-02-02 05:21:32
【问题描述】:
我想要一个这样调用的宏:
GCC_WARNING(-Wuninitialized)
展开成这样的代码:
_Pragma("GCC diagnostic ignored \"-Wuninitialized\"")
我没有运气让它工作,因为预处理器连接和字符串化的常用技巧似乎不适用,或者我不知道如何在这里应用它们。
【问题讨论】:
我想要一个这样调用的宏:
GCC_WARNING(-Wuninitialized)
展开成这样的代码:
_Pragma("GCC diagnostic ignored \"-Wuninitialized\"")
我没有运气让它工作,因为预处理器连接和字符串化的常用技巧似乎不适用,或者我不知道如何在这里应用它们。
【问题讨论】:
在预处理器魔法的帮助下:
#define HELPER0(x) #x
#define HELPER1(x) HELPER0(GCC diagnostic ignored x)
#define HELPER2(y) HELPER1(#y)
#define GCC_WARNING(x) _Pragma(HELPER2(x))
GCC_WARNING(-Wuninitialized)
【讨论】:
diagnostics 而不是diagnostic——我已经在上面的答案中修复了它。
如果宏参数用单引号括起来也可以接受吗?如果是这样,你可以使用这个:
#define GCC_WARNING(x) _Pragma("GCC diagnostic ignored '" #x "'")
当像 GCC_WARNING(-Wuninitialized) 这样调用它时,它会扩展为
_Pragma("GCC diagnostic ignored '" "-Wuninitialized" "'")
我必须在这里使用 C 的字符串连接行为(printf("a" "b"); 与 printf("ab"); 相同),因为在宏中使用 "'#x'" 可以避免 x 被扩展。
【讨论】:
_Pragma 在字符串连接之前解释它的参数,所以它会看到两个字符串,而不是一个。与printf 不同,它是一个遵循特殊规则的特殊构造。
_Pragma 是一些自定义调试功能,但现在我看一下宏的名称,我应该更清楚。
_Pragma 不是 GCC 特定的。它是 C99 标准的一部分,允许宏扩展为 pragma。但是,用户询问了特定于 GCC 的用例,但该问题对于通用 pragma 仍然有效。