home *** CD-ROM | disk | FTP | other *** search
/ NetNews Usenet Archive 1992 #27 / NN_1992_27.iso / spool / comp / lang / c / 16707 < prev    next >
Encoding:
Internet Message Format  |  1992-11-17  |  7.2 KB

  1. Path: sparky!uunet!ontek!mikey
  2. From: mikey@ontek.com (euphausia superba)
  3. Newsgroups: comp.lang.c
  4. Subject: Re: qucik, merge, shell and bubble sort
  5. Message-ID: <2188@ontek.com>
  6. Date: 17 Nov 92 22:33:48 GMT
  7. References: <1e1cnvINNt2t@usenet.INS.CWRU.Edu>
  8. Organization: Ontek Corporation -- Laguna Hills, California
  9. Lines: 159
  10.  
  11. In comp.lang.c, cc015@cleveland.Freenet.Edu (Vito T. Kwan) writes:
  12. |     I want to take a look at these four sorting method in C, does anyone
  13. | know where can I get (ftp) them?
  14.  
  15. I have implementations of quick, merge, and bubble sort; send 
  16. email to me if you can't find them through other channels.
  17.  
  18. Many people have posted timings for sort routines over the
  19. years; I was dissatisfied with the level of detail, so I grabbed
  20. a few sort routines and did some hacking and measured some
  21. of the not-so-obvious aspects of how sort algorithms perform
  22. under extreme conditions.  This is scientific only in the
  23. sense that the numbers I got were repeatable to one or two
  24. significant digits.  
  25.  
  26. The columns in the following tables have these meanings:
  27.  
  28.   compares: Number of callbacks to the comparison function.
  29.         On the few occasions I've gprof'd a sort operation, most 
  30.         of the time is spent in the comparison function, so I 
  31.         consider this the most interesting column.
  32.  
  33.   stack:    Amount of stack space used (roughly).
  34.         Obviously, the way I measured this was non-portable,
  35.  
  36.   heap:     Amount of heap space used as reported by mallinfo.uordblks
  37.  
  38.   user:     User time as reported by times(tms.tms_utime)
  39.         This is supposed to be accurate to 1/60th of a second.
  40.  
  41.   system:   System time as reported by times(tms.tms_stime)
  42.         This is also supposed to be accurate to 1/60th of a second.
  43.  
  44. The rows describe the input array and the behavior of the 
  45. comparison function.
  46.  
  47.   random:   The input data is generated by rand(), and the 
  48.         comparison function reports truthfully.
  49.  
  50.   ascend:   The data being sorted is already in the correct
  51.         order.  This is a useful case for sorting
  52.         indexes which are pretty much already in order;
  53.         bubble sort handles this case well, but results
  54.         of bubble sort are excluded here, mostly because
  55.         bubble sort is silly.
  56.  
  57.   descend:  The input data is exactly in reverse order.
  58.  
  59.   fib asc:  The data is random, but the comparison function
  60.         always says that its first argument is less than
  61.         its second argument.
  62.  
  63.   fib asc:  The data is random, but the comparison function
  64.         always says that its first argument is greater than
  65.         its second argument.
  66.  
  67.   suprise:  The comparison function returns a random value.
  68.  
  69. Now, some of these are really obscure situations that just
  70. *shouldn't* happen with real data and well-written comparison
  71. functions.  But I've found that some of the most time-consuming
  72. sorts are done at the request of the user, and are ones
  73. in which the user can specify several possibly interrelated
  74. keys.  I worried about what would happen if the user managed
  75. to find a combination that would result in something other
  76. than a complete ordering.
  77.  
  78. My comments are interspersed with the results.
  79.  
  80. banzai# test_sort 5000 
  81. HZ = 60
  82. element size = 8
  83. number of elements = 5000
  84.  
  85.  
  86. *** qsort ***
  87. data         compares      stack       heap       user       system
  88. random:         66554        768          0       3.68       0.00
  89. ascend:         57727        960          0       3.00       0.00
  90. descend:        57728        960          0       3.03       0.00
  91. fib asc:        57727        960          0       2.78       0.05
  92. fib desc: ^C
  93. surprise:       61797        864          0       3.75       0.00
  94.  
  95. [This qsort is the one supplied with SunOS 4.1.  It performs well
  96.  under most circumstances but goes into an infinite loop when the 
  97.  comparison always returns 1.  The infinite loop seems to be of
  98.  such a character that the comparison function is being called
  99.  with ever decreasing addresses and so presumably could cause
  100.  segmentation faults under some circumstances.  It's usage of
  101.  stack space and heap space are perfectly fine for modern CPUs.]
  102.  
  103. *** merge_sort ***
  104. data         compares      stack       heap       user       system
  105. random:         55240       1152      40004       2.98       0.02
  106. ascend:         32004       1152      40004       1.92       0.03
  107. descend:        29804       1152      40004       1.72       0.03
  108. fib asc:        32004       1152      40004       1.73       0.00
  109. fib desc:       29804       1152      40004       1.63       0.00
  110. surprise:       44434       1152      40004       2.75       0.00
  111.  
  112. [Based on other tests, the stack space is O(log(n)).  The heap space
  113.  used here is questionable; a more talented programmer might be
  114.  able implement it without using up O(n) space.  A less talented
  115.  programmer would be tempted to place it on the stack, but that's
  116.  a marginal improvement.  In terms of number of comparisons,
  117.  merge_sort's worst case is better than qsort's best case and with
  118.  one exception the same can be said of execution speed.]
  119.  
  120. *** merge_sort(maybe_sorted) ***
  121. data         compares      stack       heap       user       system
  122. random:         56248       1152      40004       3.05       0.10
  123. ascend:          7831       1152      40004       0.48       0.03
  124. descend:        30827       1152      40004       1.77       0.05
  125. fib asc:        33027       1152      40004       1.87       0.02
  126. fib desc:        6023       1152      40004       0.37       0.00
  127. surprise:       34723       1152      40004       2.22       0.00
  128.  
  129. [I modified merge_sort slightly to perform some simple checking to
  130.  see if the array (or subsections of the array) are already in order.  
  131.  It adds about 2% to the number of comparisons in the "normal" case, 
  132.  but for sorting an index which is "almost" sorted already this
  133.  cuts the time down dramatically.]
  134.  
  135. *** quick_sort ***
  136. data         compares      stack       heap       user       system
  137. random:         71409       1536         12       4.82       0.02
  138. ascend:         51822        960         12       2.88       0.00
  139. descend:        54924       1248         12       3.80       0.00
  140. fib asc:     12497500     479808         12     601.07       1.42
  141. fib desc:    12497500          0         12     597.93       1.15
  142. surprise:       57198        672         12       3.97       0.00
  143.  
  144. [The quick sort is adapted from the one found on page 87 of K&R 2; they 
  145.  disclaim it as sub-optimal, for good reason it seems.  I haven't
  146.  had the time to rewrite it though I did fix the infinite loop
  147.  problem, at a marginal cost in speed.  The quadratic behavior
  148.  in the case of a deceptive comparison routine should probably
  149.  not be held against it.]
  150.  
  151. --
  152.  
  153. The actual results are not true for all time and all machines.  The
  154. execution time for these algorithms when using non-brain-damaged
  155. comparison routine are all within a factor of 2.  Sorting a bigger
  156. array brings out the differences more clearly, but at least between
  157. qsort and merge sort the improvement is rather minor.
  158.  
  159. I planned to add a feature for changing the size of the input array
  160. automatically and analyzing the change in time and space usage to
  161. directly calculate O(whatever) for each algorithm, but I'm a bit busy
  162. at the moment.  (Posting to usenet to be precise.)  I'll also be
  163. adding heapsort and shellsort algorithms; if anyone has a qsort-like
  164. drop-in replacement for either or both of those I'd appreciate
  165. a copy.
  166.  
  167.      der krill
  168.  
  169.