【问题标题】:Passing the value of a variable to macro in C将变量的值传递给C中的宏
【发布时间】:2011-02-16 15:03:22
【问题描述】:

我正在尝试将变量的值传递给 C 中的宏,但我不知道这是否可行。示例:

#include <stdio.h>

#define CONCVAR(_n) x ## _n

int main () {
   int x0, x1, x2, x3, x4, x5, x6, x7, x8, x9;
   int i;

   for (i = 0; i <= 9; i++) CONCVAR(i) = i*5;

   return 0;
}

在这里,我正在尝试使用宏为所有 x_ 变量赋值,使用 ## 标记。我知道我可以使用数组轻松实现这一点,但这仅用于学习目的。

CONCVAR(i) 被替换为 xi,而不是 x1(如果 i == 1)。我知道定义和宏是如何工作的,都是关于替换的,但我想知道是否可以将 i 的值而不是字母 i 传递给宏。

【问题讨论】:

  • 你应该简单地使用数组。它永远不会以这种方式工作,即使它会,除了它只是可怕的代码之外,几乎没有什么可以从中学到的。如果您想在数组后面达到峰值,请改用指针(并为脚上的许多洞做好准备)。
  • @delnan:这看起来更像是使用/理解## 而不是使用数组的练习,但我不确定。 en.wikipedia.org/wiki/C_preprocessor#Token_concatenation
  • 作为一般经验法则,每个类似于函数或接受参数的宏都是不好的编程习惯。
  • @Lundin:嗯,它可以有它的用途。是的,相当罕见,在这些情况下,您可能会考虑使用具有您正在模拟的功能的高级语言 - 但与某些实际项目可能使用的三元组不同。
  • @Lundin 我知道这不是一个重要的功能,但我很好奇。

标签: c c-preprocessor


【解决方案1】:

i 的值替换为宏是不可能的,因为宏替换发生在您的代码编译之前。如果您使用的是 GCC,则可以通过添加“-E”命令行参数来查看预处理器输出(但是请注意,您将看到所有#include 都插入到您的代码中。)

C 是一种静态语言,您无法在运行时决定符号名称。但是,如果您使用数组并使用下标引用元素,那么您尝试实现的目标是可能的。根据经验,如果您有许多变量,例如 x0、x1 等,您可能应该使用数组之类的容器。

【讨论】:

    【解决方案2】:

    不,因为i 只存在于运行时。宏扩展发生在编译时

    【讨论】:

      【解决方案3】:

      不,它不会起作用。 C/C++ 预处理器就是这样,一个“预编译”时文本处理器。因此,它对在源代码中找到的文本进行操作。

      这就是为什么它需要文字“i”,将其传递到您的宏中,将其扩展为源代码中的文字“xi”。然后将其传递给编译器。然后编译器开始解析后处理的文本,发现文字标记“xi”作为一个未声明的变量,在这个过程中失败了。

      您可以获取示例源代码并将其传递给 gcc 编译器(例如,我在 cygwin 下使用 gcc,将您的代码粘贴到我命名为 pimp.c 的文件中,因为没有更好的名称)。然后你会得到以下信息:

      $ gcc pimp.c
      pimp.c: In function `main':
      pimp.c:9: error: `xi' undeclared (first use in this function)
      pimp.c:9: error: (Each undeclared identifier is reported only once
      pimp.c:9: error: for each function it appears in.)
      

      简而言之,不,你不能那样做。为了能够做到这一点,预处理器必须充当解释器。 C 和 C++(通常)不是解释型语言,预处理器也不是解释器。我的建议是非常清楚编译器和解释器(以及编译语言和解释语言之间)的区别。

      问候。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2019-12-06
        • 2013-08-03
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2023-01-29
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多