Search code examples
cfor-looppointerscrashcalloc

problem with filling a pointer array with random numbers initialised by calloc


  1. my program should create 10 Vectors each with a random dimension between 1 and 10 and each dimension filled with random numbers between 0 and 24.

    int * makeVector(int dimension) {
      int * Vector = NULL;
    
      Vector = (int*) calloc(dimension - 1, sizeof(int));
      if (NULL == Vector) exit(1);
    
      srand(time(0));
    
      for (int i = 0; i < (dimension - 1); i++) {
        Vector[i] = rand() % 25;
      }
    
      return Vector; 
    }
    
    int main() {
      srand(time(0));
    
      for (int i = 1; i <= 10; i++) {
        printf("-----%d. Vector-----\n", i);
        fflush(stdout);
        int dimension = (rand() % 10) + 1;
        int *Vector = NULL;
    
        memcpy(Vector, makeVector(dimension), dimension);
    
        for (int k = 1; k <= dimension; k++) {
          printf("%d. Dimension: %d\n", k, Vector[k - 1]);
        }
        if (Vector) {
          free(Vector);
          Vector = NULL;
        }
      }
      return 0;
    }
    
  2. My Problem: There are no warnings and no errors showing up! Though the For-Loop in the makeVector function doesnt seems to work at all.

    for (int i = 0; i < (dimension - 1); i++) {
         Vector[i] = rand() % 25;
    }
    

int i only equals 0 the first time and nothing happens. The For-Loop skips and the program gets terminated with the exit value:-1.073.741.819

PS: Im pretty new to programming ... could interpreted the Debugger wrong.

Thank you in advance!


Solution

  • your main problem is :

    memcpy(Vector, makeVector(dimension), dimension);
    

    while Vector is a null pointer, so the behavior is undefined

    do

    Vector = makeVector(dimension);
    

    An other problem is to redo srand(time(0)); is makeVector, the execution time is almost nothing so you reinitialize the random generation to give you again the same values (there is almost no change to have the time changing).

    Do srand(time(0)); only one time during the execution


    In

    for (int k = 1; k <= dimension; k++) {
      printf("%d. Dimension: %d\n", k, Vector[k - 1]);
    }
    

    you access to the non initialized last entry of the vector because in makeVector :

    for (int i = 0; i < (dimension - 1); i++) {
        Vector[i] = rand() % 25;
     }
    

    must be

    for (int k = 1; k < dimension; k++) {
      printf("%d. Dimension: %d\n", k, Vector[k - 1]);
    }
    

    or of course modify the initialization loop to not lost the last entry


    Compilation and execution after the changes :

    pi@raspberrypi:/tmp $ gcc -pedantic -Wextra m.c
    pi@raspberrypi:/tmp $ ./a.out
    -----1. Vector-----
    1. Dimension: 18
    2. Dimension: 21
    3. Dimension: 22
    4. Dimension: 21
    5. Dimension: 2
    6. Dimension: 0
    7. Dimension: 24
    -----2. Vector-----
    1. Dimension: 20
    2. Dimension: 24
    3. Dimension: 13
    -----3. Vector-----
    1. Dimension: 3
    -----4. Vector-----
    1. Dimension: 5
    2. Dimension: 24
    3. Dimension: 10
    4. Dimension: 4
    5. Dimension: 20
    -----5. Vector-----
    1. Dimension: 19
    2. Dimension: 7
    3. Dimension: 24
    4. Dimension: 24
    5. Dimension: 16
    6. Dimension: 11
    -----6. Vector-----
    1. Dimension: 10
    2. Dimension: 14
    3. Dimension: 17
    4. Dimension: 9
    5. Dimension: 9
    -----7. Vector-----
    1. Dimension: 9
    2. Dimension: 8
    3. Dimension: 19
    4. Dimension: 9
    5. Dimension: 7
    -----8. Vector-----
    1. Dimension: 6
    2. Dimension: 8
    3. Dimension: 23
    -----9. Vector-----
    1. Dimension: 14
    2. Dimension: 13
    3. Dimension: 12
    4. Dimension: 13
    -----10. Vector-----
    1. Dimension: 18
    2. Dimension: 10
    3. Dimension: 3
    4. Dimension: 12
    5. Dimension: 20
    pi@raspberrypi:/tmp $ 
    

    Execution under valgrind

    pi@raspberrypi:/tmp $ valgrind ./a.out
    ==29590== Memcheck, a memory error detector
    ==29590== Copyright (C) 2002-2017, and GNU GPL'd, by Julian Seward et al.
    ==29590== Using Valgrind-3.13.0 and LibVEX; rerun with -h for copyright info
    ==29590== Command: ./a.out
    ==29590== 
    -----1. Vector-----
    1. Dimension: 21
    2. Dimension: 16
    3. Dimension: 3
    4. Dimension: 11
    5. Dimension: 11
    6. Dimension: 8
    7. Dimension: 13
    8. Dimension: 8
    9. Dimension: 23
    -----2. Vector-----
    1. Dimension: 11
    2. Dimension: 3
    3. Dimension: 5
    4. Dimension: 21
    5. Dimension: 18
    6. Dimension: 4
    -----3. Vector-----
    1. Dimension: 20
    2. Dimension: 15
    3. Dimension: 4
    4. Dimension: 17
    5. Dimension: 0
    6. Dimension: 2
    7. Dimension: 21
    -----4. Vector-----
    1. Dimension: 24
    2. Dimension: 6
    3. Dimension: 20
    4. Dimension: 10
    5. Dimension: 1
    6. Dimension: 19
    -----5. Vector-----
    1. Dimension: 19
    2. Dimension: 24
    3. Dimension: 19
    -----6. Vector-----
    1. Dimension: 7
    2. Dimension: 10
    -----7. Vector-----
    1. Dimension: 5
    2. Dimension: 6
    3. Dimension: 4
    4. Dimension: 10
    5. Dimension: 11
    6. Dimension: 2
    7. Dimension: 4
    -----8. Vector-----
    1. Dimension: 0
    2. Dimension: 1
    -----9. Vector-----
    1. Dimension: 6
    2. Dimension: 18
    3. Dimension: 12
    4. Dimension: 10
    5. Dimension: 16
    -----10. Vector-----
    ==29590== 
    ==29590== HEAP SUMMARY:
    ==29590==     in use at exit: 0 bytes in 0 blocks
    ==29590==   total heap usage: 11 allocs, 11 frees, 1,212 bytes allocated
    ==29590== 
    ==29590== All heap blocks were freed -- no leaks are possible
    ==29590== 
    ==29590== For counts of detected and suppressed errors, rerun with: -v
    ==29590== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 6 from 3)