【问题标题】:Nested macro iteration with C preprocessor使用 C 预处理器的嵌套宏迭代
【发布时间】:2017-06-28 16:25:43
【问题描述】:

使用 C 预处理器,您可以拥有某种高阶宏。像这样的:

#define ABC(f) f(a) f(b) f(c)
#define XY(f) f(x) f(y)

#define CODE(x) foo_ ## x
ABC(CODE)
#undef CODE

#define CODE(x) bar_ ## x
XY(CODE)
#undef CODE

输出是:

 foo_a foo_b foo_c
 bar_x bar_y

有没有什么技巧可以嵌套这样的迭代,做这样的事情?

#define CODE(x) foo_ ## x
NEST(ABC, XY, CODE)
#undef CODE

所以输出将是:

foo_ax foo_ay foo_bx foo_by foo_cx foo_cy

特别是,我希望 ABCXY 的定义彼此独立,这样我仍然可以单独使用 ABC 或者甚至可以执行以下操作:

#define CODE(x) foo_ ## x
NEST(XY, KLMN, ABC, CODE)
#undef CODE

为了记录,这里是解决方案:

#include <boost/preprocessor/seq.hpp>

#define ABC (a) (b) (c)
#define XY (x) (y)

#define CODE(r, prod) BOOST_PP_CAT(foo_, BOOST_PP_SEQ_CAT(prod))
BOOST_PP_SEQ_FOR_EACH_PRODUCT(CODE, (ABC) (XY))

产量:

foo_ax foo_ay foo_bx foo_by foo_cx foo_cy

【问题讨论】:

  • 根据经验,我可以告诉您,每当您深入使用宏进行元编程时,几乎可以肯定您正在创建一个糟糕的程序设计,并且几乎可以肯定这是问题的错误解决方案。 “X 宏”及其各种衍生产品将被视为最后的手段。您要解决的实际问题是什么?

标签: c macros c-preprocessor metaprogramming


【解决方案1】:

Boost Preprocessor Library 提供了几个开箱即用的宏。

BOOST_PP_SEQ_FOR_EACH_PRODUCT 将遍历以(x) (y) (z) 形式编码的两个或多个列表的笛卡尔积(在库中称为序列)。

BOOST_PP_LIST_FOR_EACH_PRODUCT 将对编码为 (x, (y, (z, NIL))) 的列表执行相同的操作。

X macro 迭代转换为这样的“序列”很简单:

#define LIST_TO_SEQ(X) (X)
ABC(LIST_TO_SEQ)

【讨论】:

    猜你喜欢
    • 2021-05-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-02-09
    • 1970-01-01
    • 1970-01-01
    • 2012-10-30
    • 2011-01-26
    相关资源
    最近更新 更多