sort linked list using BST
Hi, in FAQ, Prelude's corner in section Linked List I found this:
". Another alternative way of sorting a linked list is not obvious at first, but uses the fact that a binary tree is always sorted. Simply walk the list, removing the first item and inserting it into a binary tree. Then do an inorder traversal of the tree, inserting at the end of a new list. Often it makes sense to switch between data structures, despite what people may tell you. "
So I tried to write that. Here's my code:
Code:
/* SingleLinkedList.h*/
#ifndef SINGLELINKEDLIST_H
#define SINGLELINKEDLIST_H
enum {FAIL,SUCCES};
typedef struct Node
{
int data;
struct Node* next;
}node;
//for sort
typedef struct _BST
{
int data;
struct _BST* left;
struct _BST* right;
}BST;
int InsertHead(node**,int);
int InsertEnd(node**,int);
int InsertNext(node*,int);
int RemoveHead(node**);
int RemoveEnd(node**);
int RemoveNext(node*);
int RemoveAll(node**);
int RemoveDuplicates(node*);
int Length(node*);
void Show(node*);
node* Find(node*,int);
//for sort purpose
BST* CreateBST(node*);
void InsertBST(BST**,int);
node* Sort(node*);
node* HelperSort(BST*);
void PrintTree(BST*);
#endif
Implementation file:
Code:
#include <stdio.h>
#include <stdlib.h>
#include "SingleLinkedList.h"
int InsertHead(node** head,int data)
{
node* current=(node*)malloc(sizeof(node));
if(!current)
{
return FAIL;
}
current->data=data;
current->next=NULL;
if(*head==NULL)
{
*head=current;
return SUCCES;
}
current->next=*head;
*head=current;
return SUCCES;
}
int InsertEnd(node** head,int data)
{
node*walk=*head;
node* current=(node*)malloc(sizeof(node));
current->data=data;
current->next=NULL;
if(!current)
{
return FAIL;
}
if(!*head)
{
*head=current;
return SUCCES;
}
for(;walk->next;walk=walk->next);
walk->next=current;
return SUCCES;
}
int InsertNext(node* prev,int data)
{
node* current;
if(!prev)
{
return FAIL;
}
current=(node*)malloc(sizeof(node));
if(!current)
{
return FAIL;
}
current->data=data;
current->next=prev->next;
prev->next=current;
return SUCCES;
}
int RemoveHead(node** head)
{
node* helper;
if(!*head)
{
printf("\nNothing to remove!");
return FAIL;
}
helper=*head;
*head=(*head)->next;
free(helper);
return SUCCES;
}
int RemoveEnd(node** head)
{
node* helper;
if(!*head)
{
printf("\nNothing to remove!");
return FAIL;
}
for(helper=*head;helper->next->next;helper=helper->next);
free(helper->next);
helper->next=NULL;
return SUCCES;
}
int RemoveNext(node* prev)
{
node* helper;
if(!prev)
{
return FAIL;
}
helper=prev->next;
prev->next=helper->next;
free(helper);
return SUCCES;
}
int RemoveAll(node** head)
{
node* save;
if(!*head)
{
return FAIL;
}
while(*head)
{
save=(*head)->next;
free(*head);
*head=save;
}
return SUCCES;
}
int RemoveDuplicates(node* head)
{
node* helper=head;
node* tmp;
if(!helper)
{
return FAIL;
}
while(helper->next)
{
if(helper->data==helper->next->data)
{
tmp=helper->next->next;
free(helper->next);
helper->next=tmp;
}
else
{
helper=helper->next;
}
}
return SUCCES;
}
int Length(node* walk)
{
int len=1;
if(!walk)
{
return FAIL;
}
while(walk=walk->next)
{
len++;
}
return len;
}
void Show(node* walk)
{
if(!walk)
{
printf("There are no elements in the list!");
return;
}
printf("Elements:\n");
for(;walk;walk=walk->next)
{
printf("%d ",walk->data);
}
printf("\n");
}
node* Find(node*walk,int data)
{
if(!walk)
{
return NULL;
}
for(;walk;walk=walk->next)
{
if(walk->data==data)
return walk;
}
return NULL;
}
BST* CreateBST(node* head)
{
BST* root=NULL;
while(head)
{
InsertBST(&root,head->data);
head=head->next;
}
return root;
}
void InsertBST(BST** root,int data)
{
if(!*root)
{
*root=malloc(sizeof(BST));
(*root)->data=data;
(*root)->left=NULL;
(*root)->right=NULL;
return;
}
else
{
if((*root)->data>data)
InsertBST(&(*root)->left,data);
else
InsertBST(&(*root)->right,data);
}
}
node* Sort(node* head)
{
node* sortlist;
BST* root=CreateBST(head);
RemoveAll(&head);
sortlist=HelperSort(root);
return sortlist;
}
node* HelperSort(BST* root)
{
node*head=NULL;
if(!root)
{
return NULL;
}
HelperSort(root->left);
InsertEnd(&head,root->data);
HelperSort(root->right);
return head;
}
void PrintTree(BST* root)
{
if(!root)
{
return;
}
PrintTree(root->left);
printf("%d ",root->data);
PrintTree(root->right);
}
And finally test file
Code:
#include <stdio.h>
#include "SingleLinkedList.h"
int main()
{
node* head=NULL;
node*sorted;
InsertHead(&head,1);
InsertHead(&head,1);
InsertHead(&head,2);
InsertEnd(&head,3);
Show(head);
sorted=Sort(head);
Show(sorted);
return 0;
}
And, of coure it's not working properly. I think that Binary Tree is created ok, but problem is how to create new list from tree in HelperSort because head is created again and again in recursion. I was thinking to add another argument to function, int value to ensure head is created only once. But there must be another way.
Thanks for help!