Back to C Programming
2026-07-155 min read

Example 2: calloc() and free()

Learn Example 2: calloc() and free() step by step with clear examples and exercises.

Why This Matters

In this C programming lesson, we delve into dynamic memory allocation using the calloc() function and its counterpart, the free() function. These functions are indispensable for managing memory during runtime to create arrays of any size and later release them when no longer required. Dynamic memory allocation allows you to create arrays with a size that is not fixed at compile time, which is crucial in many programming scenarios such as handling user input or processing large datasets. However, it also introduces the risk of memory leaks if not handled properly. Understanding calloc() and free() will help you write more efficient and robust C programs.

Prerequisites

Before diving into this lesson, make sure you have a good grasp of the following:

  • Basic C syntax and data types
  • Pointers in C
  • Variables and constants
  • Arithmetic operators
  • Control structures (if, for, while)
  • Functions and function prototypes
  • Input/output operations using scanf() and printf()
  • Allocating memory using malloc()

Core Concept

calloc() Function

The calloc() function is used to allocate memory for an array of elements, each initialized to zero. It takes two arguments: the number of elements and the size of each element in bytes. The formula for calculating the total size of the allocated memory is as follows:

size_t size = n * sizeof(type);
void* ptr = calloc(n, sizeof(type));

Here, n represents the number of elements you want to allocate, and type stands for the data type of each element.

When calloc() allocates memory, it initializes all allocated bytes to zero. This is useful when dealing with arrays or structures where default initialization to zero is beneficial.

free() Function

Once you've finished using a block of memory allocated with calloc(), it's essential to release it back to the operating system using the free() function. This helps prevent memory leaks and ensures your program runs efficiently.

free(ptr);

Here, ptr is the pointer to the previously allocated memory block.

Example: Allocating a 10-element integer array using calloc() and freeing it

#include <stdio.h>
#include <stdlib.h>

int main() {
int* arr; // Declare a pointer to an integer array
int n = 10; // Number of elements in the array

// Allocate memory for the array using calloc() and store the pointer in arr
arr = (int*)calloc(n, sizeof(int));

if (arr == NULL) {
printf("Error: Memory allocation failed!\n");
return 1;
}

// Now you can use the array as needed...

// ...when done, free the memory using free()
free(arr);

return 0;
}

Example: Allocating a 2D array of size m x n using calloc() and filling it with random numbers

#include <stdio.h>
#include <stdlib.h>
#include <time.h>

void print_array(int** arr, int m, int n) {
for (int i = 0; i < m; ++i) {
for (int j = 0; j < n; ++j) {
printf("%d ", arr[i][j]);
}
printf("\n");
}
}

int main() {
srand(time(NULL)); // Seed the random number generator

int m, n; // User input for rows and columns of the 2D array

printf("Enter the number of rows (m): ");
scanf("%d", &m);

printf("Enter the number of columns (n): ");
scanf("%d", &n);

if (m <= 0 || n <= 0) {
printf("Error: Number of rows and/or columns must be greater than zero.\n");
return 1;
}

int** arr; // Declare a pointer to a 2D integer array

// Allocate memory for the 2D array using calloc() and store the pointer in arr
arr = (int**)calloc(m, sizeof(int*));
for (int i = 0; i < m; ++i) {
arr[i] = (int*)calloc(n, sizeof(int));
}

if (arr == NULL) {
printf("Error: Memory allocation failed!\n");
return 1;
}

// Fill the array with random numbers between 0 and 99...
for (int i = 0; i < m; ++i) {
for (int j = 0; j < n; ++j) {
arr[i][j] = rand() % 100;
}
}

// Print the content of the array...
printf("\nArray content:\n");
print_array(arr, m, n);

// ...and free the memory using free()
for (int i = 0; i < m; ++i) {
free(arr[i]);
}
free(arr);

return 0;
}

Worked Example

Allocating a 10-element integer array using calloc() and freeing it

#include <stdio.h>
#include <stdlib.h>

int main() {
int* arr; // Declare a pointer to an integer array
int n = 10; // Number of elements in the array

// Allocate memory for the array using calloc() and store the pointer in arr
arr = (int*)calloc(n, sizeof(int));

if (arr == NULL) {
printf("Error: Memory allocation failed!\n");
return 1;
}

// Now you can use the array as needed...
for (int i = 0; i < n; ++i) {
arr[i] = i * 2;
printf("arr[%d] = %d\n", i, arr[i]);
}

// ...when done, free the memory using free()
free(arr);

return 0;
}

Common Mistakes

  1. Not checking for NULL after calloc(): If calloc() fails to allocate memory, it returns a NULL pointer. Failing to check for this can lead to undefined behavior.
  1. Forgotten free(): Not freeing allocated memory when it's no longer needed may result in a memory leak.
  1. Incorrect size calculation: Make sure you use the correct data type and size when calling calloc(). Incorrect calculations can lead to memory corruption or segmentation faults.
  1. Accessing unallocated memory: Always ensure that the index is within the bounds of the allocated array to avoid accessing uninitialized memory or causing a segmentation fault.
  1. Not initializing pointers: When dealing with multidimensional arrays, it's essential to initialize each pointer in the array and allocate memory for them separately using calloc().
  1. Leaking memory when handling errors: When an error occurs during memory allocation, make sure to free any previously allocated memory before exiting the program to prevent memory leaks.

Practice Questions

  1. Write a program that takes an integer n from the user and allocates a 2D array of size n x n using calloc(). Fill the array with random numbers between 0 and 99, print it, and free the memory.
  1. Modify the previous example to handle negative input for n. If the user enters a negative number, print an error message and terminate the program.
  1. Write a program that reads a text file containing integers separated by spaces, allocates memory using calloc() to store the numbers, and frees the memory after processing.
  1. Modify the previous example to handle whitespace characters in the input file and ignore them when reading the integers.

FAQ

  1. Why should I use calloc() instead of malloc()?
  • calloc() initializes all allocated memory to zero, while malloc() does not. This can be useful when you need to create arrays with known default values or when working with binary data.
  1. Can I use calloc() for non-integer types?
  • Yes, you can use calloc() for any data type by adjusting the size parameter accordingly. Keep in mind that the memory will still be initialized to zero.
  1. Is it necessary to free() all memory allocated with calloc()?
  • Yes, it's essential to free() any memory allocated with calloc() or malloc() when it's no longer needed to prevent memory leaks.
  1. What happens if I try to free() a pointer that was not allocated with malloc() or calloc()?
  • Freeing a pointer that was not previously allocated with malloc(), calloc(), or another function that returns a pointer to dynamically allocated memory can lead to undefined behavior, such as a segmentation fault.