User Name Password Register
DaniWeb IT Discussion Community
All
What is DaniWeb IT Discussion Community?
You're currently browsing the C section within the Software Development category of DaniWeb, a massive community of 425,936 software developers, web developers, Internet marketers, and tech gurus who are all enthusiastic about making contacts, networking, and learning from each other. In fact, there are 1,619 IT professionals currently interacting right now! Registration is free, only takes a minute and lets you enjoy all of the interactive features of the site.
Please support our C advertiser: Programming Forums
Views: 2541 | Replies: 6
Reply
Join Date: May 2007
Posts: 3
Reputation: openuser is an unknown quantity at this point 
Rep Power: 0
Solved Threads: 0
openuser openuser is offline Offline
Newbie Poster

Quicksorting linked list - simple algorithm

  #1  
May 17th, 2007
I came across a simple way of quicksorting linked list which is same as iterative version of quicksort for arrays...
http://www.openasthra.com/c-tidbits/...ple-algorithm/
worth a look...

Let me know if you have any other simple algorithm for QuickSort (for sorting linked lists), should be easy to understand...

Thanks.
AddThis Social Bookmark Button
Reply With Quote  
Join Date: Apr 2007
Posts: 5
Reputation: iMalc is an unknown quantity at this point 
Rep Power: 0
Solved Threads: 1
iMalc iMalc is offline Offline
Newbie Poster

Solution Re: Quicksorting linked list - simple algorithm

  #2  
May 21st, 2007
Originally Posted by openuser View Post
I came across a simple way of quicksorting linked list which is same as iterative version of quicksort for arrays...
http://www.openasthra.com/c-tidbits/...ple-algorithm/
worth a look...

Let me know if you have any other simple algorithm for QuickSort (for sorting linked lists), should be easy to understand...

Thanks.
I had a look at that link and I'm afraid to tell you that it is of very poor quality. The spelling is horrible, and in fact it does NOT really implement list-based-quicksort.

What it actually does is implement array-based-quicksort, and treats a linked-list as an array. This leads to extremely poor performance. In fact I think that the implementation on that site is about O(n^3) or N-cubed. Not to mention it is far longer than it should be for this algorithm.

Perhaps you would consider taking a look at a page from my own personal site which I am currently putting together, instead: <URL snipped>

My explanations are currently a bit too brief, I'm constantly working on it and uploading a new copy every few days. Feel free to ask me questions about it.

Also, if you don't necessarily have to use quicksort, then you may consider looking around at some of the alternatives on that page. Again, please feel free to ask for me to provide more explanations where they would help.
Last edited by Ancient Dragon : May 21st, 2007 at 7:00 am. Reason: snipped URL
Reply With Quote  
Join Date: May 2007
Posts: 3
Reputation: openuser is an unknown quantity at this point 
Rep Power: 0
Solved Threads: 0
openuser openuser is offline Offline
Newbie Poster

Re: Quicksorting linked list - simple algorithm

  #3  
May 24th, 2007
Originally Posted by iMalc View Post
I had a look at that link and I'm afraid to tell you that it is of very poor quality. The spelling is horrible, and in fact it does NOT really implement list-based-quicksort.

I can clearly see it is manipulating linked list links

Originally Posted by iMalc View Post
In fact I think that the implementation on that site is about O(n^3) or N-cubed. Not to mention it is far longer than it should be for this algorithm.
where is the O(n^3) coming out there in the algo, I'm not convinced.

Originally Posted by iMalc View Post
Perhaps you would consider taking a look at a page from my own personal site which I am currently putting together, instead: <URL snipped>
I would like to see your algo but, URL was snipped, I do not know the reason.
Last edited by openuser : May 24th, 2007 at 11:33 am.
Reply With Quote  
Join Date: Aug 2005
Location: near St Louis, Missouri, USA
Posts: 11,166
Reputation: Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of 
Rep Power: 38
Solved Threads: 930
Moderator
Featured Poster
Ancient Dragon's Avatar
Ancient Dragon Ancient Dragon is offline Offline
Most Valuable Poster

Re: Quicksorting linked list - simple algorithm

  #4  
May 24th, 2007
I downloaded the source and tried to compile as a C program using Visual C++ 2005 Express. Lots of compile errors, probably all of them are solvable if you are alreay comfortable with C language. Don't expect to use that code as-is -- you will have to make code changes and add at least one undefined function.
Last edited by Ancient Dragon : May 24th, 2007 at 12:35 pm.
I think it's about time we voted for senators with breasts. After all, we've been voting for boobs long enough. ~Clarie Sargent, Arizona senatorial candidate
Those who are too smart to engage in politics are punished by being governed by those who are dumber. ~Plato
Reply With Quote  
Join Date: Aug 2005
Location: near St Louis, Missouri, USA
Posts: 11,166
Reputation: Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of 
Rep Power: 38
Solved Threads: 930
Moderator
Featured Poster
Ancient Dragon's Avatar
Ancient Dragon Ancient Dragon is offline Offline
Most Valuable Poster

Re: Quicksorting linked list - simple algorithm

  #5  
May 24th, 2007
The more I look at this code the less I like it -- even after fixing all compile errors the code does not work. The linked list before and after sorting are identical. The author obviously failed to compile and test this program before posting it, and he should be ashamed of himself for doing that. You would be better off not using that program.
I think it's about time we voted for senators with breasts. After all, we've been voting for boobs long enough. ~Clarie Sargent, Arizona senatorial candidate
Those who are too smart to engage in politics are punished by being governed by those who are dumber. ~Plato
Reply With Quote  
Join Date: Apr 2007
Posts: 5
Reputation: iMalc is an unknown quantity at this point 
Rep Power: 0
Solved Threads: 1
iMalc iMalc is offline Offline
Newbie Poster

Solution Re: Quicksorting linked list - simple algorithm

  #6  
May 26th, 2007
Originally Posted by openuser View Post
I can clearly see it is manipulating linked list links


where is the O(n^3) coming out there in the algo, I'm not convinced.


I would like to see your algo but, URL was snipped, I do not know the reason.
Yes it is manipulating a linked list, but it is clearly only a leaky-abstraction placed on top of an array implementation. (Leaky in that random access isn't O(1))

The O(n^3) comes from the fact that quicksort is O(n^2) when swapping nodes is O(1), but you can clearly see that SwapNodes calls FindPrev which is O(n), and O(n) * O(n^2) = O(n^3). QED.

I must appologise for posting the link to my own site, even thought I created it specifically for helping others, I may not do so. I'm sure that the Admin would not realy have thought it was spam, but I respect that they have rules to uphold and can't afford to make execptions.
You should be able to find it from the link in my sig (if that is working).
Reply With Quote  
Join Date: Aug 2005
Location: near St Louis, Missouri, USA
Posts: 11,166
Reputation: Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of Ancient Dragon has much to be proud of 
Rep Power: 38
Solved Threads: 930
Moderator
Featured Poster
Ancient Dragon's Avatar
Ancient Dragon Ancient Dragon is offline Offline
Most Valuable Poster

Re: Quicksorting linked list - simple algorithm

  #7  
May 26th, 2007
Just in case anyone is interested here is the corrected sorting algorithm in the link in the original post. It had several bugs that I fixed and sent to the admins of that site too. It sorts an linked list of integers. If you want it to sort something else, such as floats or structures you will have to make appropriate changes to the quicksort() function.

I'm not vouching for its efficiency -- there may be more efficient ways of doing it. Only saying here that it works.

  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4.  
  5. typedef struct Node Node;
  6.  
  7.  
  8. struct Node
  9. {
  10. void* info; //data
  11. Node* next; //used to point to next node
  12. };
  13.  
  14.  
  15. //this implementation doesn't use any explicit special header node
  16. //one has to maintain a start point of a list to track all other nodes
  17. //so createlist is a dummy one
  18. Node *createlist()
  19. {
  20. return NULL;
  21. }
  22.  
  23. //insert after a known node and return the node before inserted node
  24. Node *insert(Node *after, long* data)
  25. {
  26. Node* n;
  27. n = malloc (sizeof(Node));
  28. n->info = data;
  29.  
  30. //incase header node is not created
  31. if (!after)
  32. {
  33. n->next = after;
  34. return n;
  35. }
  36.  
  37. n->next = after->next;
  38. after->next = n;
  39.  
  40. return after;
  41. }
  42.  
  43. void destroylist(Node **n)
  44. {
  45. Node * tmp;
  46.  
  47. if (!n || !*n)
  48. {
  49. return;
  50. }
  51.  
  52. while(*n)
  53. {
  54. tmp = (*n)->next;
  55. free(*n);
  56. *n = tmp;
  57. }
  58. }
  59.  
  60.  
  61. //given a node in list, prints entire list after the node
  62. int printlist(Node *h)
  63. {
  64. Node* t = h;
  65.  
  66. while(t)
  67. {
  68. printf(" %d ->", *(long*)t->info);
  69. t = t->next;
  70. }
  71.  
  72. printf(" NULL\n");
  73. return 0;
  74. }
  75.  
  76.  
  77. //find previous node of curr node
  78. Node *FindPrev(Node *list, Node *curr)
  79. {
  80. for(;list && list->next; list=list->next)
  81. {
  82. if(curr == list->next)
  83. {
  84. break;
  85. }
  86. }
  87.  
  88. if (list->next != curr)
  89. {
  90. //not find any element, probably what we are
  91. //searching for is the beginning node
  92. return curr;
  93. }
  94.  
  95. return list;
  96. }
  97.  
  98. /*A complete swap algorithm which cares of
  99. several scenarios while swapping two nodes in
  100. a linked list which doesn't have any special nodes
  101. scenarios considered while swapping
  102. 1)two nodes which are far away
  103. 2)two nodes which are far away, one is node is at
  104.   beginning of the list
  105. 3)two node which are neighbors
  106. 4)two nodes which are neibhors,
  107.   one node is at beginning of the list
  108. */
  109. Node *SwapNodes(Node *list, Node *node1, Node *node2)
  110. {
  111.  
  112. Node *node1prev, *node2prev, *tmp;
  113.  
  114. node1prev = FindPrev(list, node1);
  115. node2prev = FindPrev(list, node2);
  116.  
  117. tmp = node2->next;
  118.  
  119. //check whether node to swapped is in
  120. //beggining (i.e. header node)
  121. if (node1 != list)
  122. {
  123. node1prev->next = node2;
  124. }
  125. else
  126. {
  127. //as we do not have special header node,
  128. //if the first node and some
  129. //other node, need to be swapped,
  130. //then update the list (makes new min node as
  131. //logical header)
  132. list = node2;
  133. }
  134.  
  135. //are nodes to be swapped neibgoring nodes?
  136. if (node1->next == node2)
  137. {
  138. //nodes to be swapped are neibhoring nodes,
  139. //then swap them simply
  140. node2->next = node1;
  141. node1->next = tmp;
  142. }
  143. else
  144. {
  145. //nodes to be swapped are not neibhor nodes,
  146. //they are apart
  147. //so, consider all scenarios
  148. node2->next = node1->next;
  149.  
  150. node1->next = tmp;
  151. node2prev->next = node1;
  152. }
  153. return list;
  154. }
  155.  
  156. /*an auxilory routine for getting the Nth
  157. element in the linked list*/
  158. Node *GetNthNode(Node *list, int n)
  159. {
  160. int i=1;
  161. for(i=1;i<n;i++)
  162. {
  163. list = list->next;
  164. }
  165. return list;
  166. }
  167.  
  168. /*count number of nodes between two nodes
  169. (including the start, end mentioned)*/
  170. int NumNodes(Node *list, Node *end)
  171. {
  172. int i;
  173.  
  174. for(i=1;list && (list!=end);i++)
  175. {
  176. list = list->next;
  177. }
  178.  
  179. if (list != end)
  180. {
  181. return 0;
  182. }
  183. return i;
  184. }
  185.  
  186. //total nodes in list
  187. int countnodes(Node *list)
  188. {
  189. int i = 0;
  190.  
  191. for (;list; list=list->next)
  192. {
  193. i++;
  194. }
  195.  
  196. return i;
  197. }
  198.  
  199. /*select a pivot, pivot can be selected in any way
  200. randomly, first element, median of left, center, right
  201. elemnts, etc.
  202. Here we have chosen to pick center element as pivot*/
  203. Node *SelectPivot(Node *list, Node *end)
  204. {
  205. Node *right, *noden;
  206. int n;
  207.  
  208. n=NumNodes(list, end);
  209.  
  210. noden = GetNthNode(list, (int)((float)n/2+0.5));
  211. //
  212. right = FindPrev(list, end);
  213.  
  214. if (noden != right)
  215. {
  216. //swap the pivot and right most element in the list
  217. //later pivot will be restored.
  218. SwapNodes(list, noden, right->next);
  219. return noden;
  220. }
  221. else
  222. {
  223. return noden->next;
  224. }
  225. }
  226.  
  227. /*the actual quciksort routine*/
  228. Node * quicksort(Node *list, int list_start, int list_end)
  229. {
  230. Node *pivot, *left=list, *right=list, *tmp;
  231. int i = list_start, j= list_end-1;
  232.  
  233. if (list_start >= list_end)
  234. {
  235. return list;
  236. }
  237.  
  238. right = GetNthNode(list, list_end);
  239. left = GetNthNode(list, list_start);
  240.  
  241. //select pivot
  242. pivot = SelectPivot(left, right);
  243.  
  244. right = FindPrev(left, pivot);
  245.  
  246. for(;;)
  247. {
  248. //now starts partitioning the list
  249. for(;*(long*)left->info < *(long*)pivot->info; left=left->next,i++);
  250.  
  251. for(;*(long*)right->info > *(long*)pivot->info; right = FindPrev(list,right),j--);
  252. if (i < j)
  253. {
  254. list = SwapNodes(list, left, right);
  255. tmp = left;
  256. left = right;
  257. right = tmp;
  258. }
  259. else
  260. break;
  261. }
  262.  
  263. //restore pivot
  264. list = SwapNodes(list, left, pivot);
  265.  
  266. //now sort on smaller linked lists
  267. list = quicksort(list, list_start, i-1);
  268. list = quicksort(list, i+1, list_end);
  269.  
  270. return list;
  271. }
  272.  
  273. //a wrapper for quicksort
  274. Node *QSort(Node *list)
  275. {
  276. int n;
  277.  
  278. n=countnodes(list);
  279.  
  280. //call the quick sort routine
  281. //we always number elements in linked list as
  282. //1,2..n instead of 0, 1.. n-1
  283. return quicksort(list, 1, n);
  284. }
  285.  
  286. #define TEST
  287. #ifdef TEST
  288.  
  289. int main()
  290. {
  291. int i;
  292. Node *list2 = NULL;
  293. long data[] = {8,0,7,2,5,3,6,9,4,1};
  294. //list2
  295. for(i = 0; i < sizeof(data)/sizeof(data[0]); i++)
  296. list2 = insert(list2, &data[i]);
  297.  
  298. printf("unsorted linked list:\n");
  299. printlist(list2);
  300.  
  301. printf("sorted linked list:\n");
  302. list2 = QSort(list2);
  303. printlist(list2);
  304.  
  305. destroylist(&list2);
  306. }
  307.  
  308. #endif
Last edited by Ancient Dragon : May 26th, 2007 at 6:58 pm.
I think it's about time we voted for senators with breasts. After all, we've been voting for boobs long enough. ~Clarie Sargent, Arizona senatorial candidate
Those who are too smart to engage in politics are punished by being governed by those who are dumber. ~Plato
Reply With Quote  
Reply

Only community members can participate in forum threads. You must register or log in to contribute.

DaniWeb C Marketplace
Currently Active Users Viewing This Thread: 1 (0 members and 1 guests)

 

Thread Tools Display Modes

Similar Threads
Other Threads in the C Forum

All times are GMT -4. The time now is 9:23 pm.
Forum system based on vBulletin Copyright ©2000 - 2008, Jelsoft Enterprises Ltd.
©2003 - 2008 DaniWeb® LLC