【问题标题】:Passing macro arguments by macro通过宏传递宏参数
【发布时间】:2015-12-18 13:31:17
【问题描述】:

我正在尝试将 RGB 颜色传递给一个需要三个参数的宏。 一个正常的电话应该是这样的:MACRO(255, 255, 255) 宏转换参数并与运算符一起通过 SPI 发送到图形控制器。 C 代码中的调用如下所示:cmd(MACRO(0,0,0));

由于颜色在多个场合使用,但可能会发生变化,我认为通过另一个宏定义它可能是个好主意。 所以定义一种颜色,例如#define BLACK 0,0,0 并将其插入到另一个宏中应该没问题:MACRO( BLACK ) -> cmd(MACRO( BLACK )); 但是编译器输出错误:

宏“MACRO”需要 3 个参数,但只给出 1 个

得到这个我假设提供参数的宏没有被扩展。我试图找出通过 gcc 宏文档阅读的错误,但无法解决它。我认为这是那些愚蠢的简单事情之一...... 谢谢!

更多信息: 驱动程序提供了多个宏,以三个数字 (rgb) 作为参数。我想定义一个配色方案,以便能够在每次出现时更改颜色,而不会更改超过这三个数字。

插入宏的函数需要一个无符号长整数,这就是宏产生的结果。

为什么不简单地用 0,0,0 代替术语 BLACK?

引用 gcc 宏文档:

“宏的所有参数在被替换到宏主体之前都完全进行了宏扩展。替换后,将再次扫描完整的文本以查找要扩展的宏,包括参数。”

【问题讨论】:

  • 为什么还要嵌套呢?只需在BLACK 中使用BLACK(最好添加一些前缀以使其清晰,例如COLOR_BLACK) and use MACRO(0, 0, 0)`(更改名称,例如COLOR_RGB)。更清晰,更少输入。
  • 如果你有数百个 RGB 合成宏,你很可能做错了什么。为什么还要使用宏? inline 函数同样快速且更安全。不要在函数可以完成相同工作的地方使用宏。
  • @Olaf 函数宏是我不想接触的驱动程序的一部分。而且我不想定义很多新的宏,而只是定义颜色。合乎逻辑的一点是,我有几个由驱动程序提供的宏,我希望有一个定义的配色方案,其中包含经常使用的几种颜色。当我想在配色方案中更改一种颜色时,我不想编辑它的每次使用,而是在一个地方更改它,即定义宏。
  • 我认为它首先替换了 MACRO。所以此时它发现只有一个论点。
  • 如果不完全清楚,声明“宏的所有参数在它们被替换到宏主体之前完全宏扩展。”并不是说参数在被替换到宏 call 之前完全被宏扩展。所以 BLACK 只有在替换到 MACRO 的 body 时才会完全宏扩展(它永远不会得到,因为 MACRO 需要三个参数)。

标签: c gcc macros


【解决方案1】:

您必须确保您的组合 MACRO(BLACK) 再次评估 BLACK 部分。否则,它不会“看到”分隔零的逗号。您可以将现有的 MACRO 重命名为 MACRO3(它接收 3 个参数),然后拥有

#define MACRO(...) MACRO3(__VA_ARGS__)

【讨论】:

  • 仍然不完全理解为什么它需要额外的步骤,但这是有效的!我坚持首先扩展了论点。谢谢!
  • @HeidiSalami,首先解析() 中的内容以获取参数。你只有一个,BLACK。然后,BLACK 被扩展,所以现在逗号仍然是那个唯一参数的一部分。当你用BLACK 的扩展调用MACRO3 时,参数的分离被重新完成,然后我们有3。
  • 非常感谢,知道了!
【解决方案2】:

你可能想这样定义你的宏:

#define MACRO(x, y, z) somestuffhere
#define BLACK MACRO(0,0,0)

然后这样称呼它

cmd(BLACK);

这是一个更合乎逻辑的实现。如果你定义了一个接受 3 个参数的宏,它应该接受 3 个参数而不是一个。但是,您可以在另一个宏定义中调用宏。

【讨论】:

  • 这可行,但我也想在其他宏中使用颜色定义,这不是最佳解决方案。
猜你喜欢
  • 1970-01-01
  • 2018-11-28
  • 2018-05-16
  • 2012-01-29
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多