zoukankan      html  css  js  c++  java
  • “玲珑杯”ACM比赛 Round #19 B -- Buildings (RMQ + 二分)

    Start Time:2017-07-29 14:00:00 End Time:2017-07-29 16:30:00 Refresh Time:2017-07-29 16:42:55 Private

    B -- Buildings

    Time Limit:2s Memory Limit:128MByte

    Submissions:590Solved:151

    DESCRIPTION

    There are nn buildings lined up, and the height of the ii-th house is hihi.

    An inteval [l,r][l,r](lr)(l≤r) is harmonious if and only if max(hl,,hr)min(hl,,hr)kmax(hl,…,hr)−min(hl,…,hr)≤k.

    Now you need to calculate the number of harmonious intevals.

    INPUT
    The first line contains two integers n(1n2×105),k(0k109)n(1≤n≤2×105),k(0≤k≤109). The second line contains nn integers hi(1hi109)hi(1≤hi≤109).
    OUTPUT
    Print a line of one number which means the answer.
    SAMPLE INPUT
    3 1 1 2 3
    SAMPLE OUTPUT
    5
    HINT
    Harmonious intervals are: [1,1],[2,2],[3,3],[1,2],[2,3][1,1],[2,2],[3,3],[1,2],[2,3].
    【题意】给你一个序列,然后问你有多少个区间的最大值-最小值<=k。
    【分析】我们可以用RMQ来logn查询区间最大、最小值,然后枚举每一位最为区间右端点,向左二分左端点,将区间长度加到ans即可。
     
    #include <bits/stdc++.h>
    #define inf 0x3f3f3f3f
    #define met(a,b) memset(a,b,sizeof a)
    #define pb push_back
    #define mp make_pair
    #define inf 0x3f3f3f3f
    using namespace std;
    typedef long long ll;
    const int N = 2e5+50;
    const int mod = 1e9+7;
    const double pi= acos(-1.0);
    typedef pair<int,int>pii;
    int n,k;
    int a[N];
    int mn[N][20],mx[N][20],mm[N];
    void init() {
        for(int j=1; j<=mm[n]; ++j) {
            for(int i=1; i+(1<<j)-1<=n; ++i) {
                mn[i][j]=min(mn[i][j-1],mn[i+(1<<(j-1))][j-1]);
                mx[i][j]=max(mx[i][j-1],mx[i+(1<<(j-1))][j-1]);
            }
        }
    }
    int getmx(int l,int r) {
        int k = mm[r-l+1];
        return max(mx[l][k],mx[r-(1<<k)+1][k]);
    }
    int getmn(int l,int r) {
        int k = mm[r-l+1];
        return min(mn[l][k],mn[r-(1<<k)+1][k]);
    }
    int main(){
        mm[0]=-1;
        for(int i=1; i<N; ++i)mm[i]=(i&(i-1))?mm[i-1]:mm[i-1]+1;
        scanf("%d%d",&n,&k);
        for(int i=1;i<=n;i++){
            scanf("%d",&a[i]);
            mn[i][0]=mx[i][0]=a[i];
        }
        init();
        int l,r,res;
        ll ans=0;
        for(int i=1;i<=n;i++){
            l=1;r=i;res=i;
            while(l<=r){
                int mid=(l+r)/2;
                int maxn=getmx(mid,i);
                int minn=getmn(mid,i);
                if(maxn-minn>k)l=mid+1;
                else r=mid-1,res=mid;
            }
            ans+=i-res+1;
        }
        printf("%lld
    ",ans);
        return 0;
    }
  • 相关阅读:
    根据View获取该控制器
    富文本
    自定义cell,根据数据源,要对cell的布局进行调整,没有实现调整的相应效果
    NSTimer定时器
    textFiled输入字数的控制问题之—把带输入的拼音也判断了
    iOS 最值宏定义
    ios7.1 masonry布局中出现的问题
    串行队列、并行队列、同步、异步
    商标数字整数申请流程
    商标网上申请流程
  • 原文地址:https://www.cnblogs.com/jianrenfang/p/7257227.html
Copyright © 2011-2022 走看看