gpt4 book ai didi

c - 从另一个#define 访问#define 中声明的变量

转载 作者:太空宇宙 更新时间:2023-11-04 06:33:02 25 4
gpt4 key购买 nike

我有这个代码

struct counter_info {
atomic_t counter;
char *name;
} __attribute__((packed));

extern struct counter_info __start_counters;
extern struct counter_info __stop_counters;

#define __DOSOMETHING(F) \
do{ \
static struct counter_info __counter_info_##F \
__attribute((__section__("counters"))) \
__attribute((__used__)) = { \
.name = #F, \
}; \
atomic_set(&__counter_info_##F.counter, 0); \
\
}while(0)

我这样称呼这个宏:

__DOSOMETHING(FOO)

我想从其他代码访问 __counter_info_##F

#define __DOSOMETHINGELSE(F)                                \
do{ \
atomic_inc(&__counter_info_##F.counter); \
}while(0)

使用 __DOSOMETHINGELSE(FOO)

但是我从编译器那里得到了一个未声明的错误。这是为什么?可以吗?

编辑:

确切的错误是错误:‘__counter_info_FOO’未声明(首次在此函数中使用)注意:在宏“__DOSOMETHINGELSE”的扩展中

最佳答案

您无法从另一段代码获取该结构,因为您已在花括号 block 内声明它。 C 范围规则禁止访问该 block 之外的代码。即使您让宏生成正确的名称也是如此:__counter_info_F 而不是 __counter_info_FOO。

顺便说一句,这不是#define 问题。当 C 看到代码时,所有宏处理都已完成,编译器只看到预处理器生成的标记。

找到一种不用宏就可以完成工作的方法……然后找出一个宏表示来简化编码。

一种方法是使用不使用 do 循环的宏来封闭这些变量。现在的问题是生成唯一的名称。仔细查看这些宏,您会发现这就是创建一次性循环以解决的问题...重复名称创建双重定义。如果您打开宏生成的代码,则必须以另一种方式解决重名问题……可能是通过添加宏参数。

有一件事,作为记录:您不需要像 do 或 for 这样的复合语句来包含普通 block 。只需用大括号括起来就足够了。可以去掉开头的“do”和“while(0);”最后,得到同样的效果。

关于c - 从另一个#define 访问#define 中声明的变量,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18625268/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com