use malloc to set an array of strings then clear it

Viewed 211

I want to make an array of string using malloc, and then clear ALL the allocated memory, I believe that I use malloc correct but I can't understand what I'm doing wrong when I try to clear it:

#include <stdlib.h>
#include <stdio.h>
#include <string.h>
void print_arr(char* arr[]);
void clear_arr(char* arr[], int size);
int main()
{
    int number = 10;
    char **myarr = malloc((number+1)*sizeof(char*));
    for (int i = 0; i <= number; i++)
    {
        myarr[i]=NULL;
    }
    for (int i = 0; i < number; i++)
    {
        char str[] = "word";
        int len = strlen(str);
        myarr[i]=malloc((len+1)*sizeof(char));
        strcpy(myarr[i], str);
    }
    print_arr(myarr);
    clear_arr(myarr, number);
    print_arr(myarr);
    free(myarr);

   return 0; 
}
void print_arr(char* arr[])
{
    for (int i = 0; arr[i] != NULL; i++)
    {
        printf("%s\n",arr[i]);
    }

}
void clear_arr(char* arr[], int size)
{
    for (int i = 0; i < size; i++)
    {
        free(arr[i]);
    }

}

but my output for number = 3 is:

word
word
word
Pi╛
word
word

it's look like that only the first "cell" of the array is getting free and the other doesn't effected. what wrong with my clear_arr function? I'm using VScode to compile if that matters...

1 Answers

That's because you try to print something that you free'd. The free function deallocate the memory but you still have the address in the array.

What you can do is:

void clear_arr(char* arr[], int size)
{
    for (int i = 0; i < size; i++)
    {
        free(arr[i]);
        arr[i] = NULL;
    }

}

This way, the print function won't loop through an array of free'd pointers.

There is a better way to malloc and copy a string, you can use the function strdup.

Your code could be optimized this way:

int number = 10;
char **myarr = malloc((number+1)*sizeof(char*));
for (int i = 0; i < number; i++)
{
  myarr[i] = strdup("word");
}

myarr[number] = NULL;
Related