声明零大小矢量

时间:2010-11-23 10:43:22

标签: c

以下是什么意思?

struct foo
{
...
char  bar[0];    // Zero size???
};

我问过我的同事,他们告诉我这跟写void* bar一样。

据我所知,C指针只是一个4字节的变量(至少在32位机器上)。编译器如何知道bar [0]是一个指针(因而长4个字节)?这只是语法糖吗?

4 个答案:

答案 0 :(得分:5)

你的同事说谎了。 (可能不是故意的,但不要对他们或任何事情生气。)

这称为灵活的数组成员,在C99中写为char bar[];,在C89中写为char bar[1];,有些编译器会将其写为char bar[0];。基本上,你只使用指向结构的指针,并在结尾处分配额外的空间:

const size_t i = sizeof("Hello, world!");
struct foo *p = malloc(offsetof(struct foo, bar) + i);
memcpy(p->bar, "Hello, world!", i);
// initialize other members of p
printf("%s\n", p->bar);

这样,p->bar存储一个字符串,其大小不受数组声明的限制,但仍然在与struct的其余部分相同的分配中完成(而不是需要会员为char *,需要两个malloc和两个free才能进行设置。

答案 1 :(得分:3)

克里斯的回答是正确的,但我可能会略微区别对象。

int n = ...; // number of elements you want
struct foo *p = malloc(offsetof(struct foo, bar[n]));

然后用

迭代它
for (int i = 0; i < n; ++i) {
  p->bar[i] = ...;
}

关键是Chris的答案在sizeof(char)==1之后有效,但对于另一种类型,你必须明确乘以sizeof *bar

答案 2 :(得分:0)

这应该是编译时错误!只能为动态分配的数组分配0大小。

答案 3 :(得分:0)

也可以通过指针访问数组(索引是隐式指针)。 所以我怀疑,如果他们告诉你,这将被解释为指针。因为它是一个零长度数组,它可能会指向下一个值(我希望在该结构中有一些东西?)。

这是怀疑,而不是知识。 :)

这不是你怎么做的事情...... 如果他们想要一个指针,他们应该使用指针。如果他们不能告诉你它为什么会存在,那就不应该了。