zoukankan      html  css  js  c++  java
  • hdu 6231

    K-th Number

    Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 262144/262144 K (Java/Others)
    Total Submission(s): 518    Accepted Submission(s): 213


    Problem Description
    Alice are given an array A[1..N] with N numbers.

    Now Alice want to build an array
    B by a parameter K as following rules:

    Initially, the array B is empty. Consider each interval in array A. If the length of this interval is less than
    K , then ignore this interval. Otherwise, find the K -th largest number in this interval and add this number into array B .

    In fact Alice doesn't care each element in the array B. She only wants to know the
    M -th largest element in the array B . Please help her to find this number.
     
    Input
    The first line is the number of test cases.

    For each test case, the first line contains three positive numbers N(1N105),K(1KN),M . The second line contains N numbers Ai(1Ai109) .

    It's guaranteed that M is not greater than the length of the array B.

     
    Output
    For each test case, output a single line containing the M -th largest element in the array B .
     
    Sample Input
    2 5 3 2 2 3 1 5 4 3 3 1 5 8 2
     
    Sample Output
    3 2
     
    (这真是道好题啊
     
    题意:给定n个数,取 这n个数能组成的 所有长度不小于k的 区间 的第k大的数,把这些数放在b数组里,求b中第m大的数。
     
    解题思路:把所有的区间第K大放到一个新的数组中,然后排序,输出第M大。我二分枚举这个最后的第M大,假设为X,那么我们需要只考虑大于等于X的数字。于是相当于我们只需要判断在这个新数组中,大于等于X的数字的数量是否大于M,也即第K大大于等于X的区间的数量是否大于M。最后变成了统计第K大大于X的区间。模糊化处理之后,我们发现,如果用0、1替代,我们就能通过区间和来判定该区间的第K大是否大于等于X。如果区间和大于等于K,那么第K大就大于等于X。统计数量也相对简单了很多。我们枚举左端点,然后找右端点,知道找到一个点恰好区间和为K,那么以这个点以及这个点之后的所有点为右端点的区间第K大肯定大于等于X。这样子做看似还是O(N^2)的,但是我们发现,当左端点右移一格之后,这个右端点的最小值是不下降的,也就是说可以用类似离线处理的方法,做到用O(N)的复杂度统计。于是此题就迎刃而解了,需要注意的是,这个M可能比较大,需要用LL,然后统计区间的时候也要用LL。
     
    以上是参考博客中的思路,参考博客:http://blog.csdn.net/u013534123/article/details/78509522?locationNum=8&fps=1
     
    也就是说,如果x大于真正的答案,那么满足有k个数大于等于x的区间肯定不到m个,反之肯定多于m个(其实也不一定,比如当所有的数都相等的时候,就不一定。参考博客为了排除这个可能,用了map,也可以只需找到刚刚满足区间和大于等于m的x值便是答案,这是我的做法
     
    附ac代码:
     1 #include <cstdio>
     2 #include <cstring>
     3 #include <algorithm>
     4 #include <set>
     5 using namespace std;
     6 typedef long long ll;
     7 const int maxn = 1e5+10;
     8 int nu[maxn];
     9 int num[maxn];
    10 int flag[maxn];
    11 ll m;
    12 int ans;
    13 ll cnt;
    14 int n,k;
    15 ll check(int mid)
    16 {
    17     ans=0,cnt=0;
    18     int u=num[mid];
    19     for(int i=1;i<=n;++i)
    20     {
    21         if(nu[i]>=u)
    22         flag[i]=1;
    23         else flag[i]=0;
    24     }
    25     int ll=1,rr=0;
    26     for(ll=1;ll<=n;++ll)    //尺取法
    27     {
    28 
    29         while(rr<=n && ans<k)
    30         {
    31             rr++;
    32             if(flag[rr]) ans++;
    33 
    34         }
    35         if(rr==n+1)
    36         break;
    37         cnt+=n-rr+1;
    38         if(flag[ll])
    39         ans--;
    40     }
    41     return cnt;
    42 }
    43 int main()
    44 {
    45     int t;
    46 
    47     scanf("%d",&t);
    48     while(t--)
    49     {
    50         scanf("%d %d %lld",&n,&k,&m);
    51         for(int i=1;i<=n;++i)
    52         {
    53             scanf("%d",&nu[i]);
    54             num[i]=nu[i];
    55         }
    56         sort(num+1,num+n+1);
    57         int l=1,r=n;
    58         int ff=0;
    59         while(l<=r)
    60         {
    61             int mid=(l+r)/2;
    62             if(check(mid)>=m) l=mid+1;
    63             else r=mid-1;
    64         }
    65   //      printf("%d %d
    ",l,r);
    66         printf("%d
    ",num[r]);//二分的上界,第一个满足check(mid)>=m的值
    67     }
    68     return 0;
    69 }
    View Code
     
     
     
     
     
     
  • 相关阅读:
    成为Emacs高手01-学习自带教程
    成为Emacs高手03-学习基础Elisp
    Google Drive For Linux
    Yet Another Scheme Tutorial 02
    1、Maven 基本配置
    eclipse添加easyExport插件,打开本地文件
    原创一看便知、Maven创建web项目
    1、启动oracle的步骤
    java正则表达式【大全】
    servlet上传下载(任何格式的都可以)
  • 原文地址:https://www.cnblogs.com/zmin/p/7897067.html
Copyright © 2011-2022 走看看