7

我想使用 gcc 预处理器编写几乎相同的代码声明 500 次。假设出于演示目的,我想使用宏FOR_MACRO

#define FOR_MACRO(x) \
    #for i in {1 ... x}: \
        const int arr_len_##x[i] = {i};

并且调用FOR_MACRO(100)将被转换为:

const int arr_len_1[1] = {1};
const int arr_len_2[2] = {2};

...

const int arr_len_100[100] = {100};
4

4 回答 4

9

这不是一个好主意:

虽然原则上可能,但使用预处理器意味着您必须手动展开循环至少一次,最终您会得到一些任意实现定义的循环深度限制,并且所有语句都将在一行中生成。

更好地使用您选择的脚本语言来生成代码(可能在一个单独的可包含文件中)并将其与您的构建过程集成。

于 2013-10-01T13:35:42.170 回答
3

如果您迫切需要,您可以为此使用Order-PP 。

它是一种在预处理器中实现的脚本语言。这意味着它在概念上类似于使用脚本语言生成 C 代码(实际上,相同),只是没有外部工具,并且脚本与 C 编译器同时运行:一切都使用 C 宏完成。尽管是在预处理器上构建的,但对循环迭代、递归深度或类似的东西没有真正的限制(限制在数十亿,你不必担心)。

要发出问题示例中请求的代码,您可以编写:

#include <order/interpreter.h>

ORDER_PP(    // runs Order code
  8for_each_in_range(8fn(8I,
                         8print( 8cat(8(const int arr_len_), 8I)
                                   ([) 8I (] = {) 8I (};) )),
                     1, 101)
)

我无法理解您为什么要这样做,而不是简单地将 Python 之类的外部语言集成到您的构建过程中(Order 可能使用宏实现,但它仍然是一种需要理解的单独语言),但选项就在那里。

据我所知,订单仅适用于 GCC;其他预处理器过快耗尽堆栈(甚至是 Clang),或者不完全符合标准。

于 2013-10-03T18:46:49.997 回答
1

您确定不能以更好的方式处理它,而不是为您提供完全解决您问题的解决方案吗?

也许会更好

  • 使用一个多维数组
  • 在运行时借助数组填充数据,因为您显然想要填写每个数组的第一个条目。如果您不初始化数组,它将(假设它是在模块级别定义的)被放入.bss段而不是.data二进制文件中,并且可能需要更少的空间。
于 2013-10-01T13:57:58.907 回答
1

您可以使用例如P99来执行此类预处理器代码展开。但是由于预处理器的能力有限,这有一个限制,而且这个限制通常远低于500.

于 2013-10-01T15:14:59.227 回答