是否有一种方法可以将宏名称作为参数传递给嵌套宏,而不扩展最外层宏时它们是否可以展开?

时间:2015-02-13 06:02:36

标签: c++ c macros

(为长标题道歉,但我想不出一个不那么明确的明确标题)

我需要将(类似对象)宏的名称传递给嵌套(类似函数)的宏,如下面的(普通)示例所示:

#define ROOT_FUNC(INPUT) int v_ ## INPUT = INPUT
#define CALLER_FUNC(INPUT) ROOT_FUNC(INPUT)

#define INTA 1
#define INTB 2
#define INTC 3

现在,如果我在代码中编写ROOT_FUNC(INTA);,我会得到一个名为v_INTA的整数变量,其值为1。如果我在代码int INTD = 4;中定义变量,然后编写CALLER_FUNC(INTD);,我最终得到一个名为v_INTD的整数变量,其值为4

但如果我写CALLER_FUNC(INTA);,我会得到一个名为v_1的整数变量,其值为1,因为当时INTA已扩展为1在展开CALLER_FUNC之前展开ROOT_FUNC(即展开ROOT_FUNC(1))。

如果我将第2行更改为:#define CALLER_FUNC(INPUT) ROOT_FUNC(#INPUT)(即字符串化INPUT),则会出现编译器错误,因为要求它定义一个名为v_"1"的整数变量(无效名称)并为其赋值"1"(非整数值)。

我知道预处理器是相当原始的,但有没有办法实现我的目标?

(有关进一步说明的第二次修改,我希望CALLER_FUNC(INTA);首先展开到ROOT_FUNC(INTA);,然后展开到int v_INTA = 1; - 即我希望INTA扩展到ROOT_FUNC我在原则上寻找答案,而不仅仅是改变CALLER_FUNC以产生结果int v_INTA = 1;的任何方式,这将是微不足道的。)


P.S。 如果您想知道,我最初有一个涉及信号处理的用例(例如将SIGINT等宏名称作为嵌套宏的输入),但通过简化我的结构并放弃嵌套宏来克服这些限制;因此这个问题纯粹是学术性的。

1 个答案:

答案 0 :(得分:4)

如果你可以扩展第一个宏来获取两个参数,你可以让它像这样工作:

#define FUNC(intname, intv) int v##intname = intv
#define CALL_FUNC(intv) FUNC(_##intv, intv)

#define INT1 1
#define INT2 2

int main(void)
{
  int INTD = 4;

  CALL_FUNC(INT1);
  CALL_FUNC(INT2);
  CALL_FUNC(INTD);
}

输出(来自GCC)看起来像这样:

int main(void)
{
  int INTD = 4;

  int v_INT1 = 1;
  int v_INT2 = 2;
  int v_INTD = INTD; // not sure if you want the value of INTD here - I guess it doesn't matter?
}

我想你的意思是 - 如果我正确地读了你的问题?

令牌粘贴阻止预处理器将其扩展出来并简单地生成一个新的令牌,该令牌传递给第二个宏(然后简单地将它们粘贴在一起形成变量),值(扩展)传递给第二个论点..


EDIT1 :通过你所读的内容阅读更多内容,我猜猜上面的诀窍不是你想要的......啊......