-1

edit: solution is to declare mainMap as int **mainMap;

then when calling track_heatmap pass &mainMap

finally, inside track_heatmap do *map = rowArray;

Thanks to everyone who helped as well as an alum from my school who reached out

track.c: contains

void track_heatmap(const track *trk, double cell_width, double cell_height,
            int ***map, int *rows, int *cols) 

The parameter map: I.e. you pass in a pointer and that pointer recieves the data. So to set this up, inside of track_heatmap I've got this code, which simply creates a map (malloc'd 2D array of ints) and then specifies that the 'map' argument points to to said array.

(code inside of track_heatmap function):

if( (nRows >= 0) && (nColumns >= 0) )
    {
        // Create the 2D Array:
        int **rowArray = malloc(sizeof(int*) * nRows);
        for(int i=0; i<nRows; i++)
        {
            rowArray[i] = malloc(sizeof(int) * nColumns);
        }


        // Step through & initialize every int value in the 2D Array:

        for(int i=0; i<nRows; i++)
        {
            for(int j=0; j<nColumns; j++)
            {
                rowArray[i][j] = 0;
                // int curCell = rowArray[i][j];
            }
        }

        map = &rowArray;

Now in my main function, in a file called Heatmap.c, I actually use this. Heatmap.c

int ***mainMap = malloc(sizeof(int**));
track_heatmap(mainTrack, argWidth, argHeight, mainMap, mainRows, mainCols);

From what I understand, since we passed mainMap as the 'map' argument and track_heatmap assigns &RowArray to be 'map', then mainMap should now POINT to that same 2D array. However, when trying to access *mainMap[0][0] I get the following error:

==30007== Invalid read of size 8
==30007==    at 0x4014C4: main (Heatmap.c:120)
==30007==  Address 0x0 is not stack'd, malloc'd or (recently) free'd

It's as if mainMap has not been changed by track_heatmap. What should I do?

Asirino
  • 21
  • 4
  • By assigning a value to `map`, it doesn't change the value that `map` pointing. It just makes `map` to point other address. You should use this syntax: `*map = ...;` – hallazzang Oct 28 '19 at 03:39
  • 1
    Note that being a [Three Star Programmer](http://wiki.c2.com/?ThreeStarProgrammer) is not an accolade to be sought. – Jonathan Leffler Oct 28 '19 at 03:43
  • @ikegami but malloc itself returns a pointer, so wouldn't a malloc'd pointer to type int ** then be int ***? That's how I understand it to work. – Asirino Oct 28 '19 at 04:31
  • Sorry, you're right. Deleted comment. – ikegami Oct 28 '19 at 04:32

1 Answers1

2

Changing the value of a function's variable (including those declared as parameters) has no effect on the caller.

void bad1(int i) {
   i = 1;  // No effect on the caller.
}

void bad2(void* p) {
   p = NULL;  // No effect on the caller.
}

If you want to change a variable in the caller, you will need to pass a pointer to it.

void good1(int* i_ptr) {
   *i_ptr = 1;
}

void good2(void** p_ptr) {
   *p_ptr = NULL;
}

If you want to modify mainMap, you'll need to pass a pointer to it (&mainMap) and modify the pointed value (*ptr = ...;).

Alternatively, you could simply return the pointer (mainMap = track_heatmap(...);).

ikegami
  • 367,544
  • 15
  • 269
  • 518