Thaeryn
Thaeryn

Reputation: 23

Initialising member elements of a dynamically allocated array of structs to zero

I have had a look around but have not been able to find an answer to this question already. I am trying to create a hash table of which each element is a struct. In each struct is a variable to let the program know if the cell has been occupied, for this to work I need to set all of them to zero. The thing is it worked fine but now and then (seemingly randomly) I'd get an access violation. I thought I fixed it but when I come to grow my array the error creeps up again, leading me to believe that I have made an error. My pointer knowledge is not that good at all, so any help would be appreciated. This is what the function looks like:

HashTableCell *initialiseTable(HashTableCell *hashTable, int *tableSizePtr)
{
int i = 0;
int totalSize = *tableSizePtr * sizeof(HashTableCell);
HashTableCell *tempStartingcell;

tempStartingcell = (HashTableCell*)malloc(sizeof(HashTableCell));
*tempStartingcell = *hashTable;


while (i <= *tableSizePtr)
{
    /*we keep moving forward, need to use the first entry*/
    *hashTable = *(tempStartingcell + (i * sizeof(HashTableCell)));
    hashTable->isOccupied = 0;
    i++;
}


free(tempStartingcell);

return hashTable;
}

And before I malloced some space for the table and passed it in another function like so:

HashTableCell *hashTable;
hashTable = (HashTableCell*)malloc((sizeof(HashTableCell)*tableSize));
hashTable = initialiseTable(hashTable, tableSizePtr);

The idea is to start at the beginning and move along the correct number of spaces along per iteration of the while loop. When I come to resize I merely make a new array with double the malloced space and pass it to the initialise function but this throws up an access violation error at seemingly random indexes.

I am using VS2015 if that helps anything.

Thank you for your help.

Upvotes: 0

Views: 108

Answers (1)

G. Sliepen
G. Sliepen

Reputation: 7973

The problem is in this line:

*hashTable = *(tempStartingcell + (i * sizeof(HashTableCell)));

When you are adding an integer to a pointer, C and C++ already take into account the size of the array elements, so you should not multiply with sizeof(HashTableCell), but rather do:

*hashTable = *(tempStartingcell + i);

Otherwise, your extra multiplication will cause an access outside of the tempStartingCell array. It makes even more sense to write it like this:

*hashTable = tempStartingcell[i];

But there is more wrong with your code; if you just want to set isOccupied to zero for each element in hashTable, just do:

void initialiseTable(HashTableCell *hashTable, int tableSize)
{
    for (int i = 0; i < tableSize; i++)
        hashTable[i].isOccupied = 0;
}

Upvotes: 3

Related Questions