如何在宏内使用#ifdef?'#'后面没有跟着宏参数。

3

我接手了一个使用c语言编写的项目,其中有许多宏。

我想使用一个新的宏来检查该宏是否已启用。

但符号#在宏中被保留。如何修复我的代码?谢谢:)

#define CHECK_MACRO( macro )\
#ifdef macro
printf("defined "#macro"\n");\
#else
printf("not defined "#macro"\n");\
#endif

2
使用预处理器无法完全实现您的要求。 - R.. GitHub STOP HELPING ICE
C预处理器相当有限。它无法完成您试图要求它完成的任务。 - Tom Karzes
2个回答

1
您不能在宏内部使用预处理条件指令。一般来说,解决方案是将其反转:使用条件指令在不同情况下以不同方式定义宏。然而,对于您提出的通用宏测试宏,这种方法不起作用,并且由于它确定条件是否成立的点是在定义宏的地方,而不是使用宏的地方,因此也受到限制。
也许您可以从以下事实中得到安慰:由于函数样式宏的参数在替换为宏的替换文本之前进行扩展(除了几个不适用于代码关键部分的特殊情况),因此这永远不会起作用。
如果感兴趣的所有宏的可能值都限于可能出现为标识符或其中的短令牌列表,则有可能使用其他替代方案。如果您可以选择要测试的一小部分宏,则可能有不同的替代方案可能足够。除非您直接编写条件编译指令,否则没有任何替代方案可以完全实现您的要求,事实上,这是常规做法。

0

附注 - m4预处理器 - 历史/遗留问题。

在Unix的早期,'m4'处理器用于代码生成。它具有cpp的增强功能(或者cpp可能是m4的简化版)。特别地,它更好地支持多行宏定义,它继续被用于各种软件包中。

值得注意的是,向你的代码中添加代码生成将使其更加复杂,难以维护/调试。

例如:a.m4

define(`CHECK_MACRO', `
#ifdef $1
printf ("defined #$1\n") ;
#else
printf ("undef #$1\n") ;
#endif
')

#include <stdio.h>

void main(void)
{
  CHECK_MACRO(FOO) ;
  CHECK_MACRO(BAR) ;
}

然后构建/运行

m4 a.m4 > a.c
cc a.c
./a.out
  undef #FOO
  undef #BAR

cc a.c -DFOO
./a.out
  defined #FOO
  undef #BAR

通常,生成过程会与Makefile集成,使用规则 %.c: %.m4: m4 -s $< > $@ 其中-s选项有助于跟踪源代码行号(它将编译错误行号匹配到a.m4源文件)。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接