【问题标题】:Get value from array in #define从#define中的数组获取值
【发布时间】:2021-11-24 17:07:31
【问题描述】:

我在这样的预处理器语句中定义了一个数组:

#define myArray {0,1,2,3}

当我尝试从该数组中获取一个值而不首先将其分配给变量时,如下所示:

myArray[0];

编译器抱怨并且不允许我这样做。

这可能是因为这也不起作用:

{0,1,2,3}[0]

我怎样才能解决这个问题?我不想使用多个#define 语句,也不想先将数组分配给内存中的变量。

上下文

我想为开源微控制器项目实施补丁。 RAM空间有限,这里的整个数据流都是静态的。

我想遵循配置文件中的代码风格,它使用了很多像上面这样的数组定义。

另一方面,我不想将 RAM 空间浪费在可以直接完成的无用变量上。

【问题讨论】:

  • ... 我认为inline 数组不会被放入编译后的可执行文件中的静态内存中,这将解决您的问题。
  • 虽然通常可执行文件大小不是一个大问题。你的实际问题是什么?为什么不想让它成为一个真正的数组呢?
  • 当你有一些大型结构或数组的大型配置并希望通过更改初始值设定项列表来交换它们时,通常会有这样的宏。这意味着您将使用 [i] 而不是宏访问实际变量。
  • 我不确定 ((int[4]){1,2,3,4}) 之类的东西是否保证数组不在 RAM 中。此外const myArray[] = {0,1,2,3}; 也可能将您的阵列不放入 RAM。这完全取决于您的平台。
  • ...我的意思是const int myArray[] = {0,1,2,3};

标签: arrays c c-preprocessor


【解决方案1】:

#define 实际上定义了一个宏,然后编译器在编译时扩展它以创建您想要的可执行代码。

所以你可以使用:

#define MYARRAY {0,1,2,3}
int testArray[] = MYARRAY;
int element = testArray[0];

MYARRAY[0] 对编译器来说毫无意义,因为没有足够的信息说明如何将宏扩展为可执行代码,因此它会标记错误。

提醒一句,尽管在上面的示例中,testArray 的大小不是由 MYARRAY 宏分配的数据决定的,尽管它包含由它定义的值,因此任何返回的值sizeof(...) 操作可能比您预期的要大。

【讨论】:

  • en.cppreference.com/w/c/language/array_initialization - 你可能想重写你的最后一段......
  • 不是批评,而是要思考的迂腐点:宏被替换,不一定扩展。有时宏替换会导致代码更短,而不是更长。
  • @Eric - 感谢您的输入,英语的奇迹。在这种情况下,我并不是说代码的大小增加了,只是宏语句被定义的代码替换了,在所有情况下,这不仅仅是宏名称,否则你会长手编写代码而不是使用宏。
【解决方案2】:

这可以通过compound literals 完成。

你可以这样做

#define myArray ((int[4]){1,2,3,4})

我不建议以这种方式使用复合文字。它们不太可能是您实际问题的最佳解决方案。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-03-25
    • 2014-04-21
    • 2014-03-30
    相关资源
    最近更新 更多