桶排序——最快最简单的排序

版权声明:共同提高:) https://blog.csdn.net/u011436427/article/details/82562339

参考的内容:《啊哈算法》

1.推倒过程
这里写图片描述

2.eg
输入n个0-1000之间的整数,将它们从大到小排序;
对0-1000之间的整数进行排序,需要1001个桶子,来表示0-1000之间每一个数出现的次数。
每个桶的作用就是标记每个数出现的次数,用book(有标记的意思)来表示*

具体的代码如下:

#include<stdlib.h>
#include<stdio,h>

int main()
{
    int a[1001];
    int data;
    for(int i=0;i<=1000;i++)
        a[i]=0;
    int b;
    scanf("%d",&b);//b为待排序的数
    for(int i=1;i<=b;i++)
    {
        scanf("%d\n",&data);//把每个变量读到data中
        a[data]++;//用桶子去记录
    }

    for(int i=1000;j>=0;j--)//倒序判断for(int i=0;i<=1000;i++)
        for(int j=1;j<=a[i];j++)//出现几次,就将桶子打印几次
            printf("%d",i);

    return 0;
}

验证:
10
8 100 50 22 15 6 1 1000 999 0
结果是
1000 999 100 50 22 15 8 6 1 0

3.时间复杂度

N:为待排序数的个数
M:为桶的个数

so:时间复杂度为O(N+M)。

4.桶排序稍加改动正好可以起到去重的效果
eg:
输入有 2 行,第 1 行为一个正整数,表示有 n 个同学参与调查(n≤100)。第 2 行有 n
个用空格隔开的正整数,为每本图书的 ISBN 号(假设图书的 ISBN 号在 1~1000 之间)。
输出也是 2 行,第 1 行为一个正整数 k,表示需要买多少本书。第 2 行为 k 个用空格隔
开的正整数,为从小到大已排好序的需要购买的图书的 ISBN 号。

例如输入:
10
20 40 32 67 40 20 89 300 400 15
则输出:
8
15 20 32 40 67 89 300 400

方法一:第一种方法:先将这 n 个图书的 ISBN 号去重,再进行从小到大排序并输出
#include <stdio.h>
int main()
{
int a[1001],n,i,t;
for(i=1;i<=1000;i++)
a[i]=0; //初始化
scanf("%d",&n); //读入n
for(i=1;i<=n;i++) //循环读入n个图书的ISBN号
{
    scanf("%d",&t); //把每一个ISBN号读到变量t中
    a[t]=1; //标记出现过的ISBN号
}
for(i=1;i<=1000;i++) //依次判断1~1000这个1000个桶
{
    if(a[i]==1)//如果这个ISBN号出现过则打印出来
    printf("%d ",i);
}
getchar();getchar();
return 0;
}

方法二:先从小到大排序,输出的时候再去重
#include <stdio.h>
int main()
{
int a[101],n,i,j,t;
scanf("%d",&n); //读入n
for(i=1;i<=n;i++) //循环读入n个图书ISBN号
{
scanf("%d",&a[i]);
}
//开始冒泡排序
for(i=1;i<=n-1;i++)
{
for(j=1;j<=n-i;j++)
{
if(a[j]>a[j+1])
{ t=a[j]; a[j]=a[j+1]; a[j+1]=t; }
}
}
printf("%d ",a[1]); //输出第1个数
for(i=2;i<=n;i++) //从2循环到n
{
    if( a[i-1] != a[i] ) //如果当前这个数是第一次出现则输出
    printf("%d ",a[i]);
}
getchar();getchar();
return 0;
}

猜你喜欢

转载自blog.csdn.net/u011436427/article/details/82562339