Page 49 - C-Language
P. 49
{
int * pdata;
size_t n;
printf ("Enter the size of the array: ");
fflush(stdout); /* Make sure the prompt gets printed to buffered stdout. */
if (1 != scanf("%zu", &n)) /* If zu is not supported (Windows?) use lu. */
{
fprintf("scanf() did not read a in proper value.\n");
exit(EXIT_FAILURE);
}
pdata = calloc(n, sizeof *pdata);
if (NULL == pdata)
{
perror("calloc() failed"); /* Print error. */
exit(EXIT_FAILURE);
}
free(pdata); /* Clean up. */
return EXIT_SUCCESS;
}
This program tries to scan in an unsigned integer value from standard input, allocate a block of
memory for an array of n elements of type int by calling the calloc() function. The memory is
initialized to all zeros by the latter.
In case of success the memory is releases by the call to free().
Iterating through an array efficiently and row-major order
Arrays in C can be seen as a contiguous chunk of memory. More precisely, the last dimension of
the array is the contiguous part. We call this the row-major order. Understanding this and the fact
that a cache fault loads a complete cache line into the cache when accessing uncached data to
prevent subsequent cache faults, we can see why accessing an array of dimension 10000x10000
with array[0][0] would potentially load array[0][1] in cache, but accessing array[1][0] right after
would generate a second cache fault, since it is sizeof(type)*10000 bytes away from array[0][0],
and therefore certainly not on the same cache line. Which is why iterating like this is inefficient:
#define ARRLEN 10000
int array[ARRLEN][ARRLEN];
size_t i, j;
for (i = 0; i < ARRLEN; ++i)
{
for(j = 0; j < ARRLEN; ++j)
{
array[j][i] = 0;
}
}
And iterating like this is more efficient:
https://riptutorial.com/ 25

