Массивы переменного размера и calloc в C - PullRequest
7 голосов
/ 16 января 2009

Об обсуждении динамической памяти здесь: "Введение в указатели C и динамическая память"

Автор утверждает:

Блок памяти, подобный этому, может эффективно использоваться в качестве более гибкого массива. Этот подход на самом деле гораздо чаще встречается в реальных программах на Си. Это также более предсказуемо и гибко, чем «массив переменного размера»

Тип блока памяти, о котором он говорит, таков:

const int size = 5;
int * array = calloc(size, sizeof(int));

и затем использование другого указателя для перебора массива:

int * index = array;
for (i = 0; i < size; i++) {
    *index = 1; // or whatever value
    index++;
}

Мой вопрос: чем этот метод лучше стандартного массива переменного размера, как этот?

int array[variable];

или динамический:

char name[] = "Nick";

Автор действительно не проливает много света на то, почему я должен предпочесть первый метод второму. Или более конкретно: как это более «предсказуемо и гибко»?

Ответы [ 5 ]

10 голосов
/ 16 января 2009

Если вы объявляете int array[variable], память будет выделяться в стеке, что не очень хорошо для больших, относительно постоянных структур данных (таких, которые вы, возможно, захотите вернуть). Вам не нужно освобождать память вручную, если вы используете синтаксис массива, поскольку он освобождается, когда выходит из области видимости. calloc, с другой стороны, будет динамически выделять память во время выполнения в куче. Вы должны будете освободить его сами, как только закончите.

8 голосов
/ 16 января 2009

Я согласен с ocdecio, что не позволяет

int array[variable]

позволяет некоторым типам переменных и выражений иметь размер массива. Но в дополнение к этому, вещи, выделенные с malloc и семьей, могут быть изменены с помощью realloc.

3 голосов
/ 26 июля 2011

Использование массивов переменного размера в стеке в качестве автоматической переменной (вместо кучи с использованием calloc / malloc / new / etc) - неплохая идея для процесса, который будет выполняться в течение длительного времени и должен будет и уничтожить много маленьких массивов. Это связано с тем, что стек гарантированно не фрагментируется, а память может и будет фрагментирована. Если вы пишете прошивку или службу, которая должна работать годами без остановки, вам почти запрещено использовать malloc или new.

2 голосов
/ 20 января 2017

Автоматические массивы переменной длины разрешены в ISO C99, и в качестве расширения GCC принимает их в режиме C90 и в C ++. Поэтому не забудьте установить флаг компилятора -std = c99 или -std = gnu99. Следующий пример будет работать

#include<stdio.h>

int main()
{
    int n;
    printf("\n\tEnter the number of digits: ");
    scanf("%d", &n);

    char str[n];
    for(int i=0; i < n; i++) {
        scanf("%s", &str[i]);
    }

    printf("\n\tThe entered digits are: %s", str);
return 0;
}

Я гарантирую, что: -)

0 голосов
/ 16 января 2009

Потому что

int array[variable];

недопустимо в стандартном C - вы можете определить длину массива только с константой. (например, ваш

char name[] = "Nick";

пример, который не переменной длины.

Таким образом, необходимо использовать распределитель памяти, такой как calloc (), если вы хотите создать массив длины на основе программной переменной.

Только не забудьте освободить () его.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...