0

I have the following array describing a game board:

square * board = (square *)malloc(sizeof(square)*n*n);

How can I initalize such an array with its elements pointing to further game boards of the above declaration?

That is, I want to initialize slices of the overall board array; like so (pseudocode):

boards[0] -> [0,0,...0]
boards[1] -> [0,0,...0]
boards[2] -> [0,0,...0]

I must use malloc() to allocate the boards array.

I have already tried this way:

square (*t_board)[11]; 
t_board = malloc(sizeof(player)*n*n*11);

But I got the error: "use of undeclared indentifier 't_board'; did you mean 'board'?"

gen
  • 9,528
  • 14
  • 35
  • 64

2 Answers2

1

First allocate memory for the array with pointers and then the boards.

square **boards;
int nbr_boards = 5;
int n = 24;

//Allocate space for pointers
boards = malloc(nbr_boards * sizeof *boards);

//Allocate space for each board
for (int i = 0; i < nbr_boards; ++i)
        boards[i] = malloc(n * n sizeof **boards);

You can use this as

boards[BOARD_INDEX][SQUARE_INDEX]

To later free it you have to loop through the pointers again:

for (int i = 0; i < nbr_boards; ++i)
        free(boards[i]);
free(boards);
Forss
  • 778
  • 1
  • 4
  • 13
1

Regardless of the type, allocating a NxN array takes one of the following forms:

If N is known at compile time, or if variable-length arrays are supported, it's easy:

T (*arr)[N] = malloc( sizeof *arr * N );

Elements are accessed as arr[i][j]. When you're done, you'd free them as

free( arr );

If N is not known at compile time and VLAs are not supported and all array elements must be contiguous, then you'd need to allocate a 1D array and compute the offset:

T *arr = malloc( sizeof *arr * N * N );
...
x = arr[ i * N + j ];

If the array elements don't have to be contiguous, you can do a piecewise allocation:

T *arr = malloc( sizeof *arr * N );
if ( arr )
{
  for ( size_t i = 0; i < N; i++ )
  {
    arr[i] = malloc( sizeof *arr[i] * N );
  }
}

You'd access this array as arr[i][j], but since you allocated it piecewise, you must free it the same way:

for ( size_t i = 0; i < N; i++ )
  free( arr[i] );
free( arr );

If you want to initialize your array elements to all-bits-0, use calloc instead of malloc:

T (*arr)[N] = calloc( N, sizeof *arr );

If you want to initialize your array elements to something other than all-bits-zero, then that depends on what T looks like. If T is, say, a structure type containing two integer elements, and you're using a C99 or later compiler, you could use a compound literal combined with memcpy:

memcpy( arr[i], ( struct foo [] ){ {1,2}, {3,4}, {5,6}, {7,8} ... } );
John Bode
  • 119,563
  • 19
  • 122
  • 198
  • +1 Wrote the answer I would have - saved me time. Minor style idea: maybe `malloc( N * sizeof *arr )` vs. `malloc( sizeof *arr * N )` as it matches `nmemb, size` order of `calloc( N, sizeof *arr )`. Of course the same allocation results with `malloc()` regardless of how the product is formed. – chux - Reinstate Monica Oct 24 '14 at 21:52