从0开始学算法--排序(1.8桶排序)

算法理解:

  桶排序是对计数排序的一种优化,在计数排序中x应该放在计数数组下表为x的位置上,这样如果重复数字较少,计数数组每个位置的利用率就非常小。

  桶排序是将一系列大小近似的数字放在一个位置(每个桶维护一条有序的链表),这样提高每个位置的利用率,以提高效率.

以A【】={1,21,23,41,49}为例

假设每个桶里有10中元素,那么桶排序的结构如下图所示。

#include <algorithm>
#include <iostream>
#include <cstring>
#include <vector>
#include <cstdio>
#include <cmath>
#include <queue>

using namespace std;

const int maxn=1e5+10;

typedef struct node{
    int key;
    struct node* next;
}KeyNode;

void bucket_sort(int keys[],int size,int bucket_size){
    KeyNode **bucket_table=(KeyNode**)malloc(bucket_size*sizeof(KeyNode*));
    for(int i=0;i<bucket_size;i++){    //初始化桶
        bucket_table[i]=(KeyNode*)malloc(sizeof(KeyNode));
        bucket_table[i]->key=0;
        bucket_table[i]->next=NULL;
    }
    for(int i=0;i<size;i++){
        KeyNode* node=(KeyNode*)malloc(sizeof(KeyNode));
        node->key=keys[i];
        node->next=NULL;
        int index=keys[i]/10;//给数据分类的方法(关系到排序速度,很重要)
        KeyNode *p=bucket_table[index];
        if(p->key==0){
            p->next=node;
            p->key++;
        }
        else{
            while(p->next!=NULL&&p->next->key<=node->key){//=的时候后来的元素会排在后面
                p=p->next;
            }
            node->next=p->next;
            p->next=node;
            (bucket_table[index]->key)++;
        }
    }
    KeyNode* k=NULL;
    for(int i=0;i<bucket_size;i++){
        for(k=bucket_table[i]->next;k!=NULL;k=k->next){
            printf("%d ",k->key);
        }
    }
}
int main(){
    int n;int a[maxn];
    scanf("%d",&n);
    for(int i=0;i<n;i++){
        scanf("%d",&a[i]);
    }
    bucket_sort(a,n,100);
    return 0;
}

例一:

  给你一个数组,找到差值绝对值最小是多少?

解:最简单的思路就是先排序,之后遍历一遍,时间复杂度是O(nlogn),那么能否O(n)求解呢,是可以的。

  如果有n个数,那么我们把最大到最小值之间的数字分到n-1个桶里,必然会有两个数字在一个桶里(鸽巢原理)(抽屉原理),最小值值可能是这个桶的最小值和上一个桶的最大值的差,或者两个在同个桶的数字,对于不同的桶我们遍历一遍,对于相同的桶又回到了最初的问题,即给你一个数组,找到差值绝对值最小是多少?,这样相同的桶就递归处理,即可使效率达到比较高的状态。

原文地址:https://www.cnblogs.com/wz-archer/p/11689628.html

时间: 2024-10-31 16:23:04

从0开始学算法--排序(1.8桶排序)的相关文章

啊哈!算法之快速排序与桶排序

啊哈!算法之快速排序与桶排序 1.快速排序算法 快速排序由 C. A. R. Hoare(东尼·霍尔,Charles Antony Richard Hoare)在1960 年提出,之后又有许多人做了进一步的优化.在数列种随机找出一个基准数,因为数列是杂乱的,所以取首项为基准数.从后往前找到比基准数大的位置,再从前往后找到比基准数小的位置,交换元素:右游标向前移动与左游标向后移动,它们相遇时用基准数的位置与相遇的位置交换.此时原来数列以相遇的位置被划分为了两个需要排序的数列,再次执行上述过程:当左

复习数据结构:排序算法(七)——桶排序

桶排序是一种稳定的排序方法,也是一种外排序. 桶排序的时间复杂度:最坏情况运行时间:当分布不均匀时,全部元素都分到一个桶中,则O(n^2),当然[算法导论8.4-2]也可以将插入排序换成堆排序.快速排序等,这样最坏情况就是O(nlgn).最好情况运行时间:O(n). 也就说,前面介绍的排序算法要么是O(n^2),要么是O(nlogn),只有桶排序是可能实现O(n)排序的,但是对数据是有要求的. 基本思想:是将阵列分到有限数量的桶子里.每个桶子再个别排序(有可能再使用别的排序算法或是以递回方式继续

0基础学算法 第二弹 排序

大家好啊,这是0算法基础学算法系列第二篇,上次我在第一弹里讲了关于流程图的内容,我寻思着,这次讲些什么好呢,于是我决定,教大家一个很基础的算法,那就是排序,排序有很多方法,如果你有更多方法请在评论区里留言哦. 排序在程序中特别实用,常用的有快速排序,桶排序,冒泡排序,插入排序等等,在这里我不建议使用冒泡排序或者插入排序,建议桶排序和快速排序,这两个排序非常实用,时间复杂度低,理解起来也很容易,首先,你先思考一下,怎么用程序进行排序,然后你再来看看你的思路合理不合理,最后试着用程序实现它,实现后你

排序算法(一)-桶排序

桶排序,顾名思义,为要拍排序数组分配一些的”桶“来排序,什么意思呢?假如你有一个数组,其中包含10个元素,其中最大的数字是90,你就分配个90个以上的桶(假如定义一个int a[101]),你可以看到,10个数定义一个含100个元素的数组用来排序(当然,a[100]随便啦,你定义int a[100],a[193]都可以,只要这个元素的个数多于要排序数组的最大数,这都是你估计的,所以你尽量数组往大里面定义,原因你看排序过程即可),很费空间,但是很省时间.下面说一个排序过程. 假如你第一个数字是3,

排序算法&lt;No.2&gt;【桶排序】

算法,是永恒的技能,今天继续算法篇,将研究桶排序. 算法思想: 桶排序,其思想非常简单易懂,就是是将一个数据表分割成许多小数据集,每个数据集对应于一个新的集合(也就是所谓的桶bucket),然后每个bucket各自排序,或用不同的排序算法,或者递归的使用bucket sort算法,往往采用快速排序.是一个典型的divide-and-conquer分而治之的策略. 其中核心思想在于如何将原始待排序的数据划分到不同的桶中,也就是数据映射过程f(x)的定义,这个f(x)关乎桶数据的平衡性(各个桶内的数

从0开始学算法--排序(1.5归并排序)

算法理解: 一个数组长度为n,他的前m个元素是升序的,后n-m个元素升序的,怎么使整个数组变成一个升序数组? 如n=6,m=3 1 3 5 2 4 6 1 2 3 4 5 6 排序前 排序后 #include <algorithm> #include <iostream> #include <cstring> #include <vector> #include <cstdio> #include <cmath> #include &

从0开始学算法--排序(1.7快速排序)

算法理解: 对于无序数组里的任意一个数字V,总有一部分数字小于V,一部分数字大于V.如果我们将比V小的数字放在V的前面,比V大的数字放在后面,那V所在的位置就是整个数组排序后V应该在的位置. 同时我们得到了两个连续的无序数组,和归并排序一样左右递归处理即可. #include <algorithm> #include <iostream> #include <cstring> #include <vector> #include <cstdio>

从0开始学算法--排序(1.12c++利用标准库排序)

1,简单数组按升序排序 sort(a,a+n); #include <algorithm> #include <iostream> #include <cstring> #include <vector> #include <cstdio> #include <cmath> #include <queue> using namespace std; const int maxn=1e5+10; int a[maxn]; i

从0开始学算法--数据结构(2.3队列)

顾名思义:队列就像排序一样,先排队的人先得到处理 队列与栈类似:队列是一个先进先出表 首先考虑数组模拟,如果线性数组模拟,会导致占用空间过多,为什么?数组模拟栈会遇到这样的问题吗? 因为队列是一个先进先出表,比如加入5个元素占用的是数组下表的0-4号位置,这时候删除两个元素,0-1号位置.为了维护这个队列的结构就会导致0-1号位置占用但不利用. 栈取出的是数组尾部的元素,所以不会占用额外的空间. 优化:“将数组变为环形”(模的意义). 如果我们每次加入元素是给数组下表取模,那么整个数组就变成了环