Search code examples
carrayssortingbubble-sort

Bubble sorting an array with nulls in C


I'm trying to create a bubble sort with nulls in the middle in C.
The code works ok when the array is ordered in a way so the nulls are at the end of the array (hense the "continue" condition works).

My array looks like this: [John,David,NULL,Grace,NULL,NULL] on which I run this function:

void SortContacts(char * people[]) {
    int i,j;
    char *tempswap;
    for (i=0; i<storage-1; i++) {
        for (j=0; j<storage-i-1; j++) {
                if (people[j+1]==NULL) {
                    continue;
                }
            if (strcmp(people[j],people[j+1]) > 0) {
                tempswap = people[j];
                people[j] = people[j+1];
                people[j+1] = tempswap;
            }
        }
    }
}

When executing with the NULL in the middle of the array the exe crashes.


Solution

  • You cannot strcmp a NULL value. Although you are guarding against a strcmp of people[j+1] being NULL, you don't check people[j].

    Try the following (untested), which simply provides a strcmp function which treats a NULL like "".

    int
    strcmpwithnull(const char *a, const char *b)
    {
        return strcmp(a?a:"", b?b:"");
    }
    
    void SortContacts(char * people[]) {
        int i,j;
        char *tempswap;
        for (i=0; i<storage-1; i++) {
            for (j=0; j<storage-i-1; j++) {
            if (strcmpwithnull(people[j],people[j+1]) > 0) {
                    tempswap = people[j];
                    people[j] = people[j+1];
                    people[j+1] = tempswap;
                }
            }
        }
    }
    

    If you want a NULL to be treated as greater than any other string, then try (again untested):

    int
    strcmpwithnull(const char *a, const char *b)
    {
        if (a == b)
            return 0; /* handles 2 NULLs and two strings at the same location */
        else if (!a)
            return 1;
        else if (!b)
            return -1;
        else
            return strcmp(a, b);
    }
    

    If you want them to be less than any other string (including the empty string), swap the return 1 and return -1.