Search code examples
cbit-fieldsqsort

How do I handle bitfields and qsorting together?


The language is C. Recently here I asked for and received help making the function qsort work for an array of structures.

I am now studying bit-fields and trying to make a program that uses a structure that uses another structure using bitfields and then sorting it out. But when I compile it, I get error at the compare function that "dereferencing pointer to incomplete type" and I had many trials again but still can't make it work. Can you folks help me?

Here's the code:

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

int compare(const void * a, const void * b)
{
    struct emp *orderA = (struct emp *)a;
    struct emp *orderB = (struct emp *)b;

    return (orderA->d.year - orderB->d.year);
}

int main()
{
    int i;
    struct date{
        unsigned day : 5;
        unsigned month : 4;
        unsigned year : 12;
    };

    struct emp {
        char name[10];
        struct date d;
    };

    struct emp e[5];
    for(i = 0; i < 5; i++)
    {
        scanf("%s %d %d %d", e[i].name, e[i].d.day, e[i].d.month, e[i].d.year);
    }
    qsort(e, 5, sizeof(struct emp), compare);

    for(i = 0; i < 5; i++)
    {
        printf("%s %d %d %d\n", e[i].name, e[i].d.day, e[i].d.month, e[i].d.year);
    }
    return 0;
}

Solution

  • Why this doesn't work

    Since you've defined struct emp inside your main function, it only exists inside your main function.

    As such, when you attempt to cast to struct emp* in your compare function, the type does not exist.

    If you want this code to work, you should move

    struct emp {
        char name[10];
        struct date d;
    };
    

    out of your main function and above your compare function.

    Ideally you should move it into its own header file and include that.

    The same applies to your struct date since it is used inside struct emp. So move

    struct date{
        unsigned day : 5;
        unsigned month : 4;
        unsigned year : 12;
    };
    

    out of your main function as well.


    Scopes in C

    Keep in mind as a general rule in C that any non-static identifier declared or defined inside a scope (meaning between a set of {}) is local to that scope and cannot be accessed outside of that scope.