1

我已经看到了类似问题的其他答案,但似乎没有一个对我有用。假设我有一个动态数组:

int* myarray;
myarray = malloc(myarray, 4*sizeof(int));
myarray[0] = 1;
myarray[1] = 2;
myarray[2] = 3;
myarray[3] = 4;

我想要做的是删除(并且免费,因为数组会越来越大)数组的第一个元素。我很清楚如果缩小,realloc它会删除数组的最后一个元素。对此有什么想法吗?这可能吗?

提前致谢!

4

4 回答 4

6

我能想到的一种方法是做


memmove(myarray, myarray+1, 3*sizeof(int))

然后用于realloc缩小数组。我不确定在 C 中有更有效的方法可以做到这一点。

于 2013-01-30T03:22:40.187 回答
0

通常,无法对阵列执行“删除”操作。也许您想创建和使用链表?

C++ 有其std::vector支持这一点。它将做的是将稍后出现的元素向前移动 1 个元素。您可以实现这一点,然后再调用realloc

如果只需要删除第一个元素,则将它们反向存储是一个明显的解决方法。

于 2013-01-30T03:22:11.213 回答
0

您必须将所有其他元素分流到一个。从概念上讲,它是这样的:

for( int i = 0; i < 3; i++ ) p[i] = p[i+1];

正如其他人所提到memmove的,针对移动重叠的内存段进行了优化,而不是使用上述循环。

随着阵列变大,移动数据仍然效率低下。每次添加项目时重新分配一个数组更糟糕。一般建议是不要这样做。只需跟踪您的数组有多大以及其中当前存储了多少项目。当您种植它时,将其种植大量(通常您会将其扩大一倍)。

听起来您可能想要一个循环队列,在其中预先分配数组,并且当您推入和弹出项目时,头和尾指针相互追逐。

于 2013-01-30T03:23:36.093 回答
0

我不认为你会在 C 中找到一种正确/干净的方法来做到这一点。C++ 作为一些这样做的图书馆,几乎所有面向 OO 的语言都可以做到这一点,但不是 C。我能想到的是移动内存,是的,调用 realloc,或者将您想要释放的位置设置为已知值,您将在内存重用策略中将其视为空。

另一种解决问题的方法是通过数组的动态实现。不知道你是否想去那里,但如果你想,这里有一些简短的例子。

由于您只保存整数,因此像这样的结构:

typedef struct DynamicArray_st{
 int x;
 struct DynamicArray_st *next;
}DynamicArray;

可以根据程序需要分配和释放元素。它还允许在中间、开始或结尾插入,frees 也是如此。

您将执行此操作的方式是保存指向此动态类型开头的指针,然后对其进行迭代。问题是您无法通过 [] 表示法访问数据。迭代是必要的,这使得处理时间变得更重。

除此之外,你的代码会变成这样:

DynamicArray *array = malloc(sizeof(DynamicArray)); /*Just a first element that will stay empty so your Dynamic array persists*/
 array->next = NULL;
 DynamicArray *aux = array;
 DynamicArray *new;
 for(i = 0; i<4; i++){
    new = malloc(sizeof(DynamicArray));
    new->next = NULL;
    new->x = i+1;
    aux->next = new;
    aux = new;
 }

在这里,您有一个结构序列,每个结构都指向下一个结构,并且内部有一个整数。如果现在你会做类似的事情:

aux = array->next; /*array points to that empty one, must be the next*/
 while(aux != NULL){
   printf("%d\n",aux->x);
   aux = aux->next;
 }

你会得到输出:

1
2
3
4

释放第一个元素很简单:

  aux = array->next;
  array->next = aux->next;
  free(aux);

如果您尝试绘制它(结构是框,next/aux/next 是箭头),您会看到一个框的箭头勾勒出一个框 - 您想要释放的框。

希望这可以帮助。

于 2013-01-30T03:49:11.240 回答