0

有没有办法在不定义大小的情况下初始化数组。当循环运行时,数组的大小会自行增加,它会重新分配数组。

4

3 回答 3

2

您可以在不指定大小的情况下初始化数组,但除非您在使用它之前为其分配空间,否则它不会有用。通常,当您在 C 中声明变量时,编译器会在“堆栈”上为该变量保留特定数量的内存。但是,如果您希望数组能够在整个程序中增长,那么这不是您要寻找的,因为为“堆栈”上的变量分配的空间量是静态的。

因此,解决方案是让程序在运行时而不是编译时决定为变量分配多少内存。这样,当程序运行时,您将能够决定您的变量需要保留多少空间。

在实践中,这称为动态内存分配,它是在 C 中使用函数 malloc() 和 realloc() 完成的。我建议阅读这些功能,我认为它们对您非常有用。

如果您有后续问题,请随时提出。

最后一件事!

每当您使用 malloc() 为变量分配内存时,您应该记住在程序结束时或在使用完变量时对该变量调用函数 free()。

于 2013-04-28T07:09:21.300 回答
2

没有开箱即用的东西。您必须创建自己的类似数组的数据结构来执行此操作。如果你小心的话,它应该不会很难实现。

您正在寻找的大致是一种数据结构,该结构在创建时分配(malloc例如使用 )预定义的大小并开始使用其中的连续空间作为数组的槽。然后,随着更多项目的添加,它会重新分配(例如,使用realloc)该空间。

当然,您将无法使用以前用于简单数组的索引器语法。相反,您的数据结构必须提供自己的一对set/get函数来处理上述问题。因此,该set函数将检查其参数中指定的索引,如果该索引大于数组的当前大小,则执行重新分配。然后,无论如何,将提供的值设置为指定的索引。

于 2013-04-28T07:00:47.610 回答
1

这是这种数据结构的简单实现(对于ints,但您可以将 替换为int您需要的任何类型)。为了清楚起见,我省略了错误处理。

typedef struct array_s {
    int len, cap;
    int *a;
} array_s, *array_t;

/* Create a new array with 0 length, and the given capacity. */
array_t array_new(int cap) {
    array_t result = malloc(sizeof(array_s));
    array_s a = {0, cap, malloc(sizeof(int) * cap)};
    *result = a;
    return result;
}

/* Destroy an array. */
void array_free(array_t a) {
    free(a->a);
    free(a);
}

/* Change the size of an array, truncating if necessary. */
void array_resize(array_t a, int new_cap) {
    result->cap = new_cap;
    result->a = realloc(result->a, new_cap * sizeof(int));
    if (result->len > result->cap) {
        result->len = result->cap;
    }
}

/* Add a new element to the end of the array, resizing if necessary. */
void array_append(array_t a, int x) {
    if (result->len == result->cap) {
        // max the new size with 4 in case cap is 0.
        array_resize(a, max(4, result->cap * 2));
    }
    a->a[a->len++] = x;
}

通过存储len(数组的当前长度)和cap(您为数组保留的空间量),您可以将 O(1) 中的数组扩展到 is 时的点lencap然后调整数组的大小(例如:使用realloc),也许通过将现有乘以cap2 或 1.5 或其他东西。这是大多数向量或列表类型在支持可调整大小数组的语言中所做的。我已将其编码array_append为示例。

于 2013-04-28T08:06:55.540 回答