Monday, April 9, 2012

Heapsort Algorithm implementation in C#


Today I would like to introduce another sorting algorithm: heapsort. 
Heapsort’s running time is O(n lg n). Heapsort also introduces another algorithm design technique: using a data structure, in this case one we call a "heap", to manage information. The term "heap" was originally coined in the context of heapsort, but it has since come to refer to "garbage-collected storage", such as the programming languages C#, Java provide. My heap data structure is not garbage-collected storage, and whenever I refer to heaps,  I mean a data structure rather than an aspect of garbage collection.

The heapsort algorithm starts by using "Adjust" to build a max-heap on the input array A[1..n], where n=A.Length. Since the maximum element of the array is stored at the root A[1], we can put it into its correct final position by exchanging it with A[n]. If we now discard node n from the heap—and we can do so by simply decrementing A:heap-size—we observe that the children of the root remain max-heaps, but the new root element might violate the max-heap property. All we need to do to restore the max-heap property, however, is call  Adjust(A,1), which leaves a max-heap in A[1..n-1]. The heapsort algorithm then repeats this process for the max-heap of size n - 1 down to a heap of size 2.

Here is code:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace SortComparison
{
    public class HeapSort<T> where T : IComparable<T>
    {
        
        public static void Sort(T[] A)
        {
            //build the initial heap
            for (int i = (A.Length - 1) / 2; i >= 0; i--)
                Adjust2(A, i, A.Length - 1);

            //swap root node and the last heap node
            for (int i = A.Length - 1; i >= 1; i--)
            {
                T Temp = A[0];
                A[0] = A[i];
                A[i] = Temp;
                Adjust(A, 0, i - 1);
            }
        }



        private static void Adjust(T[] list, int i, int len)
        {
            T Temp = list[i];
            int j = i * 2 + 1;

            while (j <= len)
            {
                //more children
                if (j < len)
                    if (list[j].CompareTo(list[j + 1]) < 0)
                        j = j + 1;

                //compare roots and the older children
                if (Temp.CompareTo(list[j]) < 0)
                {
                    list[i] = list[j];
                    i = j;
                    j = 2 * i + 1;
                }
                else
                {
                    j = len + 1;
                }
            }
            list[i] = Temp;
        }


    }
}

Please, feel free post any comments!

No comments:

Post a Comment