Why comparison sort has a lower bound at least nlgn,which means T(n) = Ω(nlgn)?
Decision-tree can easily tell why. A decision-tree is always a full binary tree. In camparison sort (like merge sort), every step is actually a comparison between 2 elements.And decision-tree list all these comparison cases in its body,results in its leaves.Here's the proof of the title question,
The tree must contain n! leaves, since there are n! possible sorting results. A height-h binary tree has less than 2h leaves. Thus, n! ≤ 2h. Do some math we will get h ≥ nlgn - nlge.
The height of the tree is actually the worst case of the algorithm.
Then how can a sorting algorithm do a better job?
The incomming sorting algorithms are not a comparison sort,and,unfortunately,are limited by some conditions.
Counting sort.
If the elements of a array are all integers and the range of these integers is tight,like 6,4,5,1,3,8,7 , they're all integers and,good to know,the smallest one is 1 and the largest one is 8.In this case counting sort run at a linaer time.
steps:
1.Init a array c , the keys are from lower bound to upper bound. Set them all to 0.In this case the key should be 1 to 8.
2.Traverse the unsorted array a from 0 to a.length - 1,self plus the c[a[i]].Now c[i] is count(elements in a where key=i).
3.Traverse c from 1 to c.length - 1 and set c[i] = c[i] + c[i-1]. Now c[i] is count(elements in a where key<=i).
4.Traverse a from a.length - 1 to 0 , set the result array b[c[a[i]]] = a[i] and c[a[i]] = c[a[i]] - 1.
performance:T(n) = Θ(n + k)
If the k = O(n) , we can use this algorithm for sorting things depends on the T(n).
Here is the algorithm in javascript,
1 function counting(a,u,d) 2 { 3 var c = []; 4 var b = []; 5 for(var i = u;i <= d;i++) 6 { 7 c[i] = 0; 8 } 9 for(var i = 0,j = a.length; i < j; i++) 10 { 11 c[a[i]]++; 12 } 13 for(var i = u + 1; i <= d ; i++) 14 { 15 c[i] = c[i] + c[i-1]; 16 } 17 for(var i = a.length - 1;i >=0; i--) 18 { 19 b[c[a[i]]] = a[i]; 20 c[a[i]]--; 21 } 22 return b; 23 }
Radix sort.
It is a digit by digit counting sort.I'd like to give a example to discribe the algorithem because of my poor English.
329
457
657
839
436
720
355
Assume this is a 3 cols,7 rows table. And we got the first col array 9 7 7 9 6 0 5 , let's counting sort these number just by this col and we get
720
355
436
457
657
329
839
and now we sort it by the second col, then the thrid and finnaly we get
329
355
436
457
657
720
839
That is sorted already.So the work is just 3 times of counting sort. If we do like this , the T(n) is depend on the bit "b" of the number and "k" of each cols which in this case are 3 and 7. T(n,b) = Θ(b(n + k)) that's easily to get because we just do times of counting sort.
However,If there are "n" unsorted 32-bits binary numbers , and we sort them as what we did before, we will do counting sort 32 times . That is expensive and unnecessary.The followin is the solution of this case, and this is actually the general solution of this algorithm btw.
Assume the binary numbers are of "b" bits each.Now we group the bits by "r", that means we viewed each number as having b/r bits, and each "bit" range in 2r.Now the T(n) goes like T(n,b) = Θ(b/r(n+2r)) (just replace the b by b/r and k by 2r)."r" plays a important role here, a brilliant choice of r does a great benefit. And the best choice is r = lgn.So finnally
T(n,b) = Θ(bn/lg n)
If the numbers in the range from 0 to nd - 1 , we have b = dlgn [ (2b + 2b-1 + 2b-2+ …… + 1) = nd - 1 ] , then T(n) = Θ(dn).
what a brilliant solution!