Добавление значения в конец динамического массива - PullRequest
1 голос
/ 28 декабря 2011

Ну, я изучал немного C этим зимним перерывом, и в своих приключениях я наткнулся на проблему с Dynamic Array.

Это довольно простая программа на самом деле. То, что я пытаюсь сделать, - это создать массив, который будет содержать числа ряда Фибоначчи. Вот код:

#include <stdio.h>
#include <stdlib.h>

int dynamic_arry_append(int* arry, int* number, int* size);

int main() {

    int i, n, size = 3, *arry = NULL, fibarr[size];

    printf("Dynamic array, Fibonacci series. \n");
    printf("Capture upto element: ");
    scanf("%d", &n);

    i = 0;
    // passing the first elements
    fibarr[0] = 0;
    fibarr[1] = 1;
    fibarr[2] = 1;

    while ( i < n ) {
        printf("**%d\n",fibarr[0]);
        dynamic_arry_append( arry, &fibarr[0], &size );
        fibarr[0] = fibarr[1];
        fibarr[1] = fibarr[2];
        fibarr[2] = fibarr[1] + fibarr[0];
        i++;
    }

    for ( i = 0 ; i < size ; i++) 
        printf("Element %d of the array: %d.\n", i, arry[i]);

    return 0;
}

int dynamic_arry_append(int* arry, int* number, int* size) {
    int i;

    int bacon = *size; // first name i thought of
    bacon++;
    int *new_addr = realloc(arry, bacon * sizeof(int));

    if( new_addr != NULL ) {
        arry = new_addr;
        arry[bacon-1] = *number;
        // printf for easier debugging, or so i thought
        for ( i = 0 ; i < bacon ; i++ ) 
            printf("%d\t%d\n", i+1, arry[i]);
        printf("\n");
        *size = bacon;
    } else {
        printf("Error (re)allocating memory.");
        exit (1);
    }

    return 0;
}

По крайней мере, на мой взгляд, это работает. Однако на практике я получаю забавные результаты:

Dynamic array, Fibonacci series.
Capture upto element: 5
**0 // next fibonacci number
1       5256368
2       5246872
3       1176530273
4       0

**1
1       5256368
2       5246872
3       1768053847
4       977484654
5       1

**1
1       5256368
2       5246872
3       1551066476
4       1919117645
5       1718580079
6       1

**2
1       5256368
2       5246872
3       977484645
4       1852397404
5       1937207140
6       1937339228
7       2

**3
1       5256368
2       5246872
3       1551071087
4       1953724755
5       842231141
6       1700943708
7       977484653
8       3

/* Code::Blocks output */
Process returned -1073741819 (0xC0000005)   execution time : 17.886 s
Press any key to continue.

Я действительно озадачен этой ошибкой, и после поиска вокруг я не нашел решения ... Кто-нибудь может помочь? Большое спасибо.

Ответы [ 4 ]

1 голос
/ 28 декабря 2011
#include <stdio.h>
#include <stdlib.h>

int * dynamic_array_append(int * array, int size);

int main() {

    int i, n, size=0, *array = NULL;

    printf("Dynamic array, Fibonacci series. \n");
    printf("Capture upto element: ");
    scanf("%d", &n);

    for (i=0 ; i<n ; i++)
        array = dynamic_array_append(array, i);

    for (i=0 ; i<n ; i++) 
        printf("array[%d] = %d\n", i, array[i]);

    return 0;
}

int * dynamic_array_append(int * array, int size) 
{
    int i;
    int n1, n2;
    int new_size = size + 1;
    int * new_addr = (int *) realloc(array, new_size * (int)sizeof(int));

    if (new_addr == NULL) {
        printf("ERROR: unable to realloc memory \n");
        return NULL;
    }

    if (size == 0 || size == 1) {
        new_addr[size] = size;
        return new_addr;
    }

    n1 = new_addr[size-1];
    n2 = new_addr[size];
    new_addr[new_size-1] = new_addr[new_size-2] + new_addr[new_size-3];

    return new_addr;
}

/*
Output:

Dynamic array, Fibonacci series. 
Capture upto element: 10
array[0] = 0
array[1] = 1
array[2] = 1
array[3] = 2
array[4] = 3
array[5] = 5
array[6] = 8
array[7] = 13
array[8] = 21
array[9] = 34

*/

Примечания:

  • Вновь (пере) выделенный массив должен быть возвращен обратно в main и сохранен в pointer-to-int (или) проходе pointer-to-pointer-to-int и обновлять его соответствующим образом один раз после восстановления
  • fibarr не требуется. Это не решает никаких проблем.
  • Вам не нужно пропускать size и number. Просто отправьте size, и он выберет n-1 и n-2 для вычисления n.
  • Это считается highly inefficient. Потому что, если вы знаете n, вы можете выделить память для n целых чисел за один снимок и вычислить ряд фиб.
1 голос
/ 28 декабря 2011

Проблема может заключаться в том, что переменная-указатель arry передается значением в функцию dynamic_arry_append.Это означает, что изменения, внесенные вами в переменную arry внутри этой функции, не будут отражены никакими переменными вне этой функции.Например:

int *a = NULL;

someFunc(a);

// a will still be NULL here no matter what someFunc does to it.
0 голосов
/ 28 декабря 2011

Вы не возвращаете новый адрес массива ... и вы читаете / записываете не свою память.Запустите программу со всеми сообщениями об ошибках в отладчике, и вы увидите, что проблема в этой строке:

  dynamic_arry_append( arry, &fibarr[0], &size );  
0 голосов
/ 28 декабря 2011

Вы должны объявить ваш fibarr как указатель (так называйте его по-другому), а не как массив. И вы должны передать на ваш dynamic_arry_append адрес этого указателя, например &fibarr. И вы должны инициализировать fibarr в вашем main с calloc. Наконец, вы должны динамически обновить (и сохранить, и передать) размер выделенного массива.

...