WARNING: The following is most likely overkill for what you're wanting to do. But I'm frustrated trying to track down a subtle but nasty bug and need a distraction.
If I may offer some suggestions...
First of all, IMO it's easier to insert items into a list in order than to sort an unordered list; what I would do is create an insertInOrder function that takes your list head, the new element to be added, and a predicate (a pointer to a function) that compares records, and returns the new head of the list:
Rec *insertInOrder(Rec *head, Rec *new, int (*cmp)(Rec *, Rec *))
{
if (head == NULL)
{
return new;
}
else if (cmp(new, head) < 0) // new is "less than" head
{
new->nextRec = head;
return new; // new becomes the new head of the list
}
else
{
Rec *tmp = head;
/**
* Find the first element in the list that is not "less than" new
*/
while (tmp->nextRec != NULL && cmp(new, tmp->nextRec) > 0)
{
tmp = tmp->nextRec;
}
if (tmp->nextRec == NULL)
{
// insert new at end of list
tmp->nextRec = new;
new->nextRec = NULL;
}
else
{
// insert new before tmp->nextRec
new->nextRec = tmp->nextRec;
tmp->nextRec = new;
}
// keep the current list head
return head;
}
}
Now you can order the list based on different criteria. The cmp
argument points to a function that takes two record pointers and compares them, returning -1 if the first argument is "less than" the second, 1 if the first argument is "greater than" the second, and 0 if they compare equal. For example, if you want to sort by names, define a function like
int compareNames(Rec *e1, Rec *e2)
{
int r = strcmp(e1->name, e2->name);
if (r < 0) return -1;
if (r > 0) return 1;
return 0;
}
and call insertInOrder as
head = insertInOrder(head, new, compareNames);
To sort the list, given a particular predicate: starting at the head, remove one element at a time from the existing list and add it to a new list, using the indicated predicate:
Rec *sortLinkedList(Rec *head, int (*cmp)(Rec *, Rec *))
{
Rec *newList = NULL;
while (head)
{
Rec *tmp = head;
head = head->nextRec;
tmp->nextRec = NULL;
newList = insertInOrder(newList, tmp, cmp);
}
return newList;
}
...
head = sortLinkedList(head, compareNr);
...
head = sortLinkdeList(head, compareNames);
...
head = sortLinkedList(head, compareSomethingElse);
Like Neil, I'm not terribly fond of typedefs for pointer types; experience has shown me that they cause more problems than they're worth.