0
typedef struct
{
    int blah;
    int bleh;
} Foo;

typedef struct
{
    int a;
    int b;
    Foo* arr[];
} Bar;

int main(int argc, char **argv)
{
    Bar* bar = malloc(sizeof(Bar) + sizeof(Foo) * 5);
    Foo foo1 = bar->arr[0];
    return 0;
}

foo1分配的行上,我得到“无效的初始化程序”。如果我将类型更改为Foo*,它将编译。但是如果我这样做foo1->blah = 3了,程序就会崩溃。

为什么数组元素的类型是Foo*而不是Foo?为什么程序会崩溃?

4

3 回答 3

3

arr是一个数组,Foo*因此您不能在此处将元素分配arr给 a Foo

 Foo foo1 = bar->arr[0];

第二个问题是,即使您arr正确分配内存,也需要初始化每个内存pointer,否则您将取消引用未定义行为的未初始化指针。

如果你想要一个数组,Foo那么这就是你想要的:

typedef struct
{
    int a;
    int b;
    Foo arr[];
} Bar;

那么你的其余代码不会改变。

这是使用引入的灵活数组成员C99,这里的答案讨论如何正确分配和释放。

于 2013-05-29T01:37:46.793 回答
2

数组元素的类型是Foo *因为这正是您声明它们的方式。声明Foo* arr[]代表一个Foo *元素数组。Foo当您在声明中明确表示时,您为什么期望元素是Foo *

更改foo1to的类型Foo *看起来像是一个没有多大意义的随机更改。你想做什么 - 这是你应该首先回答的问题。最后需要什么样的数组BarFoo arr[]还是Foo *arr[]

根据您的判断,您malloc似乎想FooBar. 如果是这样,您必须将数组声明更改为Foo arr[].

于 2013-05-29T01:52:03.810 回答
1

Foo* arr[]是一个指针数组,指针bar->arr[0]也是。

这工作正常:

Foo* foo1 = bar->arr[0];

要创建一个对象,Foo您可以使用以下任一方法

Foo bar1 = *bar->arr[0] // or **bar->arr; though this may be less clear 
于 2013-05-29T01:44:01.923 回答