计数排序

计数排序(Count Sort)是一个非基于比较的排序算法,该算法于1954年由 Harold H. Seward 提出。它的优势在于在对一定范围内的整数排序时,它的复杂度为Ο(n+k)(其中k是整数的范围),快于任何比较排序算法。

计数排序的思想类似于哈希表中的直接定址法,在给定的一组序列中,先找出该序列中的最大值和最小值,从而确定需要开辟多大的辅助空间,每一个数在对应的辅助空间中都有唯一的下标。

  1. 找出序列中最大值和最小值,开辟Max-Min+1的辅助空间
  2. 最小的数对应下标为0的位置,遇到一个数就给对应下标处的值+1,。
  3. 遍历一遍辅助空间,就可以得到有序的一组序列

计数排序_第1张图片

void CountSort(int* array,int size)
{
    assert(array);
    int max = array[0];//序列中的最大值
    int min = array[0];//序列中的最小值
    for(int i = 0;i < size;++i)
    {
        if(array[i] >= max)
        {
            max = array[i];
        }
        else
        {
            min = array[i];
        }
    }
    int range = max - min + 1;//需要开辟的空间大小
    int* count = new int[range];
    memset(count,0,sizeof(int)*range);//辅助空间初始化为0,0代表没有那个数

    for(int i = 0;i < size;++i)
    {
        count[array[i] - min]++;//array[i]-min是将该数对应到辅助空间的下标
    }
    int index = 0;
    for(int i = 0;i < range;++i)//遍历辅助空间
    {
        while(count[i]--)//下标处的数值是几,说明该数出现了几次
        {
            array[index++] = i + min;//将下标处的数对应回原数组
        }
    }
    delete[] count;
}

算法分析
计数排序是一种以空间换时间的排序算法,并且只适用于待排序列中所有的数较为集中时,比如一组序列中的数据为0 1 2 3 4 999;就得开辟1000个辅助空间。
时间复杂度
计数排序的时间度理论为O(n+k),其中k为序列中数的范围。
不过当O(k)>O(n*log(n))的时候其效率反而不如基于比较的排序(基于比较的排序的时间复杂度在理论上的下限是O(n*log(n)), 如归并排序,堆排序)

你可能感兴趣的:(排序算法)