0

So I got this struct Node which contains 2 fields: DataP data, void * key, DataP is just a typedef for void*.

I created a double pointer Node **table to make it like a 2D array.

I can't figure how to malloc it, I want this double pointer to act as a 2D array with 2 as number of rows and x as number of cols.

I've tried table = (Node**)malloc(sizeof(Node*)*2); but is this correct? and how do I continue from here?

Cherubim
  • 5,287
  • 3
  • 20
  • 37
Bar Vered
  • 21
  • 3
  • You need to allocate the array of pointers first, then iterate it and allocate each entry (to point to an array of objects). – barak manos Aug 21 '16 at 17:06

4 Answers4

2

I've tried table = (Node**)malloc(sizeof(Node*)*2); but is this correct?

YES you're doing it the right way. Now you've two variables of the type Node* which are table[0] and table[1]

Note that you need not cast the return value of malloc(). Here's why : click

and how do I continue from here?

Now use a for loop to assign memory to the above two variables

for(int index = 0; index < num_of_rows; index++)
{
    table[index] = malloc(no_of_columns * sizeof(Node)); 
    //don't cast the return value of malloc()
}

so next time you want to allocate memory to a double pointer, you can do it this way :

table = malloc(no_of_rows * sizeof(Node));
for(int index = 0; index < num_of_rows; index++)
{
    table[index] = malloc(no_of_columns * sizeof(Node)); 
}

//Don't forget to free() the pointers you malloced when you no longer need them

for(int index = 0; index < num_of_rows; index++)
{
    free(table[index]); 
}
free(table);
Community
  • 1
  • 1
Cherubim
  • 5,287
  • 3
  • 20
  • 37
1

Order of allocation memory for table of size ROW_NUM x COL_NUM should be the following:

1) Memory for array of pointers:

   Node ** table = malloc( sizeof(Node*) * ROW_NUM);

2) Memory for each row (loop needed)

   for(int i = 0; i < ROW_NUM; i++)
        table[i] = malloc( sizeof(Node) * COL_NUM);

Order of deallocation have to be reverse: loop with free for each table[i] first

VolAnd
  • 6,367
  • 3
  • 25
  • 43
0

You need to allocate the table first, and then allocate each one of the rows:

table = malloc(sizeof(Node*)*2);
for (int i=0; i<2; i++)
    table[i] = malloc(sizeof(Node)*x);

And don't forget to deallocate this memory when you're done using it:

for (int i=0; i<2; i++)
    free(table[i]);
free(table);
barak manos
  • 29,648
  • 10
  • 62
  • 114
0

Summarising and tweaking, it should look like this:

Node.h

#ifndef NODE_H
#define NODE_H

typedef void * DataP;

struct Node 
{
  DataP data; 
  void * key;
}


#endif

Node.c

#include <stdlib.h> /* for malloc () and free() */
#include <errno.h> /* for errno */

#include "node.h"

void nodes_free(struct Node ** ppNode, size_t rows)
{
  if (!ppNode)
  {
    return;
  }

  for (size_t row = 0; row < rows; ++row)
  {
    free(ppNode[row]);
  }

  free(ppNode);
}


int nodes_allocate(struct Node *** pppNode, size_t rows, size_t columns)
{
  if (!pppNode && !*pppNode)
  {
    errno = EINVAL;
    return -1;
  }

  *pppNode = malloc(rows * sizeof **pppNode);
  if (!*pppNode)
  {
    perror("malloc() failed on allocating rows");
    return -1;
  }

  {
    size_t row = 0
    for (; row < rows; --row)
    {
      (*pppNode)[row] = malloc(columns * sizeof *(*pppNode)[row]);
      if (!*pppNode[row])
      {
        perror("malloc() failed on allocating columns");
        break;
      }
    }

    if (row < rows) /* Allocation of columns did not completed successfully, 
                       clean up and leave. */
    {
      nodes_free(*pppNode, row);
      return -1;
    }
  }

  return 0;
}

Use those functions like this:

#include <stdlib.h> /* for EXIT_xxx macros */
#include <stdio.h> /* for perror() */

#include "node.h"


#define ROWS (5)
#define COLUMNS (7)


int main(void)
{
  struct Node ** ppNode;

  if (-1 == nodes_allocate(&ppNodes, ROWS, COLUMNS);
  {
    perror("nodes_allocate() failed");
    return EXIT_FAILURE;
  }

  /* Do stuff. */

  /* clean up. */
  nodes_free(*ppNodes, ROWS);     

  return EXIT_SUCCESS;
}
alk
  • 69,737
  • 10
  • 105
  • 255