Maximum Gap|leetcode题解

这道题可以使用桶排序的方法和基数排序的方法,对这两个方法不了解的可以参考算法导论。

这两个排序算法都可以在线性时间内对在一定范围内的数据进行排序,是能够解这道题的理论基础。

是有桶排序的思路是:

首先,对数据进行根据桶进行划分。

然后,统计桶间的最大间隔。

gmax=max(num);gmin=min(num);

当对[gmin,gmax]的范围内的数据进行均匀划分桶时,桶的区间长度bucketSize为数据范围除以区间个数,即bucketSize=(gmax-gmin)/(n-1)+1;

因此,桶的个数bucketCnt=(gmax-gmin)/bucketSize+1;

此时,桶内数据的差值在bucketSize之内,而整体数据之间一定存在差值大于区间长度bucketSize的两个数,否则,所有数据之间的差值都在bucketSize之内,

那么所有数据的形成的范围不可能是[gmin,gmax]。

程序如下所示:

struct Bucket{
    int bmin;
    int bmax;
    int bcnt;
    Bucket(int x, int y, int z){
        bmin=x;bmax=y;bcnt=z;
    }
};
int maximumGap(vector<int> &num){
    int n=num.size();
    if(n<2) return 0;
    if(2==n) return abs(num[1]-num[0]);
    auto minMax=minmax_element(num.begin(),num.end());
    int gMin=*minMax.first, gMax=*minMax.second;
    int bucketSize=(gMax-gMin)/(n-1)+1;
    int bucketCnt=(gMax-gMin)/bucketSize+1;
    vector<Bucket>bucket(bucketCnt,Bucket(INT_MAX,INT_MIN,0));
    for(int i=0;i<n;i++){
        int k=(num[i]-gMin)/bucketSize;
        bucket[k].bcnt++;
        if(num[i]<bucket[k].bmin)bucket[k].bmin=num[i];
        if(num[i]>bucket[k].bmax)bucket[k].bmax=num[i];
    }
    int pre=0,maxGap=0;
    for(int i=1;i<bucketCnt;i++){
        if(!bucket[i].bcnt)continue;
        maxGap=max(maxGap,bucket[i].bmin-bucket[pre].bmax);
        pre=i;
    }

    return maxGap;
}
使用基数排序时,参考别人的代码和C++11新特性,写出了下面AC的基于基数排序的解决方法

int maximumGap(vector<int> &num){
    for(auto bit=0;bit<31;bit++)
        stable_partition(num.begin(),num.end(),[bit](int x){return !(x&1<<bit);});

    int maxGap(0);
    for(unsigned i=1;i<num.size();i++) maxGap=max(maxGap,num[i]-num[i-1]);
    return maxGap;
}
简单的利用了C++11的特性,加快了写代码地速度,并且更加简洁!

lambda函数[bit](int x){return !(x&1<<bit);}

和自动类型识别auto,才发现C++11有挺多好用的特性,了解的有点晚了,下次出新技术,要及时快速地了解。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值