基数排序

基数排序是桶式排序的推广。——《数据结构与算法分析:C语言描述》

红心实例分析基数排序算法思想:

假设我们有10个数,范围在0-999之间,我们要将其排序。显然,我们不能使用桶式排序,考虑最坏的情况下我们将需要使用1000个桶,这样桶就太多了。我们的策略是使用多趟桶式排序(对于十进制数来说,其基数为10,对每位(个、十、百)进行桶式排序最多只需要10个桶)。我们用最低有效位(LSB)优先的方式进行桶式排序,也就是说首先对这10个数按照个位上的数字进行一次桶式排序,再对这10个数按照十位上的数字进行一次桶式排序,最后对这10个数按照百位上的数字进行一次桶式排序。这样经过三趟桶式排序后,这10个数也就排好序了。(注:对于一位数,其十位、百位均为0;对于两位数,其百位为0)

红心实例解析基数排序实现步骤:

假设10个数为:64、8、216、512、27、729、0、1、343、125,为方便起见我们将不足三位的数以高位补零的方式全部补为三位数。

高位补零后这10个数为:064、008、216、512、027、729、000、001、343、125.

 

第一趟桶式排序(个位):

000 001 512 343 064 125 216 027 008 729
0 1 2 3 4 5 6 7 8 9

 

第二趟桶式排序(十位):

008
001
000

216
512
729
027
125
 

343
 

064
     
0 1 2 3 4 5 6 7 8 9

 

第三趟桶式排序(百位):

064
027
008
001
000




125




216




343
 



512
 



729
   
0 1 2 3 4 5 6 7 8 9

 

红心基数排序算法时间复杂度分析:

我们已知桶式排序的时间复杂度为O(N+B),其中N为待排序元素个数,而B是桶数。我们又知道基数排序是以多趟桶式排序来实现的,所以基数排序的运行时间是O(P(N+B)),其中P是排序的趟数。

红心C语言实现,基于链表

#include "list.h"

#include <stdio.h>

#include <stdlib.h>

#include <math.h>



void

radix_sort(int A[], int N, int M)  /* A[]为待排序数组,N为数组A中元素个数,M为数组A中最大值的位数 */

{                                  /* 假设待排序的数全部是正整数 */

    int i, j, k, l, m, n;

    list bucket[10];

    ptr_to_node ptr;

    

    for(k = 0; k < 10; k++)

        bucket[k] = create_list();   /* 分配10个桶(链表) */ 



    for(i = 0; i < M; i++)           /* i=0(按个位上的数字排序);i=1(按十位上的数字排序)… */

    {

        l = 0;

        for(j = 0; j < N; j++)

        {

            n = A[j] / pow(10, i) ;

            m = n % 10;

            insert_to_tail(A[j], bucket[m]);  /* 按位(个、十、百…)排序,放入对应的桶中 */

        }

        for(k = 0; k < 10; k++)

        {

            ptr = bucket[k]->next;

            while(ptr != NULL)

            {

                A[l] = ptr->data;          /* 把本次(比如按照个位数排序)排序后的数按照顺序重新装入数组A,以待下次(按照下个数位的)桶排序使用 */

                l++;

                ptr = ptr->next;

            }

            //bucket[k]->next = NULL;

            make_empty(bucket[k]);         /* 把桶置空,为下一个数位排序做准备,可以用bucket[k]->next = NULL;实现此语句的功能,但未释放资源 */

        }

    }

}



int 

main(void)

{

    int i;

    int A[] = {64, 8, 216, 512, 27, 729, 0, 1, 343, 125};    

    

    printf("unsorted: ");

    for(i = 0; i < 10; i++)

        printf("%d ", A[i]);

    printf("\n");



    radix_sort(A, 10, 3);

    printf("sorted  : ");

    for(i = 0; i < 10; i++)

        printf("%d ", A[i]);

    printf("\n");



}

其中list.c和list.h源码参考:http://www.cnblogs.com/nufangrensheng/p/3579993.html

编译运行结果如下:

image

你可能感兴趣的:(基数排序)