动态分配struct属性的适当方法是什么?

时间:2014-03-19 04:46:31

标签: c struct malloc

在我开始之前,我应该说这与直接问题无关,但出于好奇和我无法找到与我之后完全相关的事情。我现在正在教自己C,我有其他几种语言的经验,所以除了如何执行某些事情之外,它没什么新鲜的。

我想在C中做一个挑战,比如构建一个可以根据需要增长一定数量的Stack,我选择使用一个结构:

#define INITIAL_STACK_SIZE 10

typedef struct Stack {
  int max_size;
  int cur_top;
  int *elements;
} Stack;

我将元素保留为空点,以便可以根据需要进行扩展,这使得构建堆栈的函数就像:

Stack *Stack_make() {
  Stack *stack = malloc(sizeof(Stack)); // This is ultimately where I become confused
  stack->max_size = INITIAL_STACK_SIZE;
  stack->cur_top = -1;
  stack->elements = malloc(sizeof(int) * INITIAL_STACK_SIZE);

  return stack;
}

正如我所指出的,我的困惑在于结构的malloc。我知道C在内存中对齐struct数据元素,所以我很好奇如果将元素指针稍后或次要地分配给struct本身,它将如何做到这一点。这是不好的做法吗?有更好的方法吗?

为了完整性,这就是我扩展堆栈的原因:

// Relevant bits only
int new_size = stack->max_size + INITIAL_STACK_SIZE;
int *elements = malloc(sizeof(int) * new_size));
if (elements != NULL) {
  memcpy(elements, stack->elements, sizeof(int) * stack->max_size);
  free(stack->elements);
  stack->elements = elements;
}

我知道这不是#34;代码审查的最佳位置"但是,如果你有改进的建议,那将是什么不值得赞赏。 实际问题:有没有更好的方法在C中执行此操作,是否有任何陷阱我会掩饰?

1 个答案:

答案 0 :(得分:2)

  

我知道C在内存中对齐struct数据元素,所以我很好奇如果将元素指针稍后或次要地分配给结构本身,它将如何做到这一点。

指针将与结构的其余部分位于相同的连续内存中,但指针指向的malloc内存将由malloc放置。realloc。 (毕竟,你可以有多个结构,指向同一个内存;显然,它不能与所有结构对齐。)

  

这是不好的做法吗?

这取决于"这个"是。如果"这"在结构中有一个指针来动态分配内存,然后没有,这不是坏习惯。

那就是说,你的特定算法并不好,因为它涉及每次复制所有内容。

  

有更好的方法吗?

是的,realloc

int new_size = stack->max_size + INITIAL_STACK_SIZE; int *elements = realloc(stack->elements, sizeof(int) * new_size); if(elements != NULL) { stack->elements = elements; } ,如果可能,将扩展先前为该指针分配的内存。如果那是不可能的,那么它将为你移动内存块(并解除分配使用的内容)。返回值是指向内存的指针,可以是相同的指针,也可以是新指针。

所以你的代码(或至少你共享的那个代码)变成了:

{{1}}

仅供参考,flexible array members(在C99中)具有可变长度,但是为结构本身分配了included in the memory。它们不适合您的需求,但考虑到有关内存对齐的问题,您可能有兴趣了解它们。