代码之家  ›  专栏  ›  技术社区  ›  Emiliano

声明零大小向量

c
  •  4
  • Emiliano  · 技术社区  · 14 年前

    以下是什么意思?

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

    我问我的同事,他们告诉我这和写作是一样的 void* bar .

    据我所知,C指针只是一个4字节的变量(至少在32位计算机上)。编译器怎么知道bar[0]是一个指针(因此有4个字节长)?这只是语法上的甜点吗?

    4 回复  |  直到 14 年前
        1
  •  5
  •   Chris Lutz    14 年前

    你的同事撒谎了。(可能不是故意的,所以不要生他们的气或其他什么的。)

    这被称为灵活数组成员,而在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 s和2 free 我们来设置它)。

        2
  •  3
  •   Alex Budovski    14 年前

    克里斯的回答是正确的,但我可能会分配对象略有不同。

    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] = ...;
    }
    

    关键是克里斯的回答有效 sizeof(char)==1 ,但对于另一种类型,必须显式地乘以 sizeof *bar

        3
  •  0
  •   Armen Tsirunyan    14 年前

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

        4
  •  0
  •   Kissaki    14 年前

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

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

    但你不会做任何事 如果他们想要一个指针,他们应该使用一个指针。如果他们不能告诉你为什么不应该在那里。