在struct中声明数组

时间:2013-04-29 08:31:26

标签: c arrays struct

我正在尝试为包含“quote”类型的数组的循环缓冲区创建一个结构。但是,引用数组必须以10的大小开始。我试图找出是否在我的.h文件或我的.c文件中声明大小为10。我的两个文件如下:

.h文件:

typedef struct{
    unsigned int time;
    double rate;

}quote;

typedef struct{

    unsigned int testNum;
    quote quoteBuffer[];

}cbuf;

cbuf* cbuf_init();

.c文件:

cbuf* cbuf_init(){

    cbuf *buffer = (cbuf *)calloc(1,sizeof(cbuf));
    buffer->testNum = 1;
    quote newQuote = {1,1.00};
    buffer->quoteBuffer[1] = newQuote;
    return buffer;


}

这些显然只是测试值,但是如果我想在cbuf结构中专门使引用数组的大小为10,我会在.h文件中声明为:

typedef struct{

    unsigned int testNum;
    quote quoteBuffer[10];

}cbuf;

或.c文件中的其他方式?

3 个答案:

答案 0 :(得分:2)

有两种方法可以在结构中使用动态数组。显而易见的当然是将它作为指针,并在需要时动态分配(或重新分配)。


另一种是使用大小为1的数组,然后分配比结构更大的大小,以适应数组:

typedef struct {
    unsigned int testNum;
    quote quoteBuffer[1];
} cbuf;

cbuf *cbuf_init(const size_t num_quotes) {
    /* Allocate for the `cbuf` structure, plus a number of `quote`
     * structures in the array
     */
    cbuf *buffer = malloc(sizeof(cbuf) + (num_quotes - 1) * sizeof(quote));

    /* Other initialization */

    return buffer;
}

/* If more quotes are needed after initial allocation, use this function */
cbuf *cbuf_realloc(cbuf *buffer, const size_t new_num_quotes) {
    buffer = realloc(buffer, sizeof(cbuf) + (new_num_quotes - 1) * sizeof(quote));

    /* Other initialization */

    return buffer;
}

现在您可以将数组用作普通数组:

cbuf *buffer = cbuf_init();
buffer->quoteBuffer[5].time = 123;

注意:我只为 9 quote结构分配额外空间,但声明我分配了十个。原因是cbuf结构在其数组中已经包含一个quote结构。 1 + 9 = 10. :))

注2:我将quote数组放在cbuf结构中,其中已有一个条目,以便向后兼容。在C世界中,在结构中没有大小的数组是一个全新的。

答案 1 :(得分:1)

如果你想在一个cbuf中使用10个引号,你也可以这样做但是静态分配的类似报价缓冲区[10]也可以这样做:

cbuf* cbuf_init(int numQuotes)
{
    cbuf *b = calloc(1, sizeof(cbuf) + numQuotes * sizeof(quote));

    return b;
}

答案 2 :(得分:1)

如果你想要一个静态大小的循环缓冲区,那么你可以在头文件中声明大小。使用#define作为缓冲区大小将使代码更具可读性和可维护性,因为您将在代码中的其他位置引用该大小。

如果希望循环缓冲区可增长,则在C文件中定义大小。然后,您必须注意跟踪大小并破坏您必须动态分配的内存。

在您的示例中,我认为您需要为报价结构分配更多空间......

cbuf *buffer = (cbuf *)calloc(1,sizeof(cbuf) + NUM_QUOTES*sizeof(struct quote));
                                             ---------------------------------

原因在于你的struct def ...

quote quoteBuffer[];

... quoteBuffer不会为结构添加大小。 quoteBuffer将指向结构末尾的一个字节,因此需要为数组的struct +内存分配内存。

编辑:Daniel Fischer的评论(感谢Daniel) - 在某些情况下,如果引入填充,quoteBuffer可能会为结构添加大小。原因是编译器可能会努力为quoteBuffer获得最佳的对齐方式。例如,通常对齐4字节边界的int。例如。结构如:

struct {
   char a;
   int b;
}

可能由编译器改为

struct {
   char a;
   char pad[3]; // compiler adds padding behind the scenes 
   int b; // align b on a 4-byte boundary
}

这个probs不适用于你的情况,因为你的struct在4字节边界上留下了quoteBuffer []。

编译器执行此操作的原因有两个。 1.在某些架构上(我认为现在不常见?),不支持未对齐的访问。 2.对齐访问更有效,即使架构允许非对齐访问,因为它是一个内存读取而不是两个内存读取加上操作。