zoukankan      html  css  js  c++  java
  • BZOJ 1717: [Usaco2006 Dec]Milk Patterns 产奶的模式

    1717: [Usaco2006 Dec]Milk Patterns 产奶的模式

    Time Limit: 5 Sec  Memory Limit: 64 MB
    Submit: 1066  Solved: 582
    [Submit][Status][Discuss]

    Description

    农夫John发现他的奶牛产奶的质量一直在变动。经过细致的调查,他发现:虽然他不能预见明天产奶的质量,但连续的若干天的质量有很多重叠。我们称之为一个“模式”。 John的牛奶按质量可以被赋予一个0到1000000之间的数。并且John记录了N(1<=N<=20000)天的牛奶质量值。他想知道最长的出现了至少K(2<=K<=N)次的模式的长度。比如1 2 3 2 3 2 3 1 中 2 3 2 3出现了两次。当K=2时,这个长度为4。

    Input

    * Line 1: 两个整数 N,K。

    * Lines 2..N+1: 每行一个整数表示当天的质量值。

    Output

    * Line 1: 一个整数:N天中最长的出现了至少K次的模式的长度

    Sample Input

    8 2
    1
    2
    3
    2
    3
    2
    3
    1

    Sample Output

    4

    HINT

     

    Source

    [Submit][Status][Discuss]

    求出后缀数组,二分答案,在height数组里找出最大的出现次数进行判断

      1 #include <bits/stdc++.h>
      2 
      3 inline char Char(void)
      4 {
      5     static const int siz = 1 << 20;
      6     
      7     static char buf[siz];
      8     static char *hd = buf + siz;
      9     static char *tl = buf + siz;
     10     
     11     if (hd == tl)
     12         fread(hd = buf, 1, siz, stdin);
     13     
     14     return *hd++;
     15 }
     16 
     17 inline int Int(void)
     18 {
     19     int ret = 0, neg = 0, c = Char();
     20     
     21     for (; c < 48; c = Char())
     22         if (c == '-')neg ^= true;
     23     
     24     for (; c > 47; c = Char())
     25         ret = ret * 10 + c - '0';
     26     
     27     return neg ? -ret : ret;
     28 }
     29 
     30 const int siz = 20005;
     31 
     32 int n, m, s[siz];
     33 
     34 int map[siz], tot;
     35 
     36 int sa[siz], rk[siz], ht[siz];
     37 
     38 inline void prework_sa(void)
     39 {
     40     static int ta[siz];
     41     static int wa[siz], wb[siz];
     42     static int ca[siz], cb[siz];
     43     
     44     for (int i = 1; i <= n; ++i)
     45         ++ca[s[i]];
     46     
     47     for (int i = 1; i <= n; ++i)
     48         ca[i] += ca[i - 1];
     49     
     50     for (int i = n; i >= 1; --i)
     51         sa[ca[s[i]]--] = i;
     52     
     53     rk[sa[1]] = 1;
     54     
     55     for (int i = 2; i <= n; ++i)
     56     {
     57         rk[sa[i]] = rk[sa[i - 1]];
     58         if (s[sa[i]] != s[sa[i - 1]])
     59             ++rk[sa[i]];
     60     }
     61     
     62     for (int l = 1; rk[sa[n]] < n; l <<= 1)
     63     {
     64         for (int i = 1; i <= n; ++i)
     65             ca[i] = cb[i] = 0;
     66         
     67         for (int i = 1; i <= n; ++i)
     68         {
     69             ++ca[wa[i] = rk[i]];
     70             ++cb[wb[i] = i + l <= n ? rk[i + l] : 0];
     71         }
     72         
     73         for (int i = 1; i <= n; ++i)
     74         {
     75             ca[i] += ca[i - 1];
     76             cb[i] += cb[i - 1];
     77         }
     78         
     79         for (int i = n; i >= 1; --i)
     80             ta[cb[wb[i]]--] = i;
     81         
     82         for (int i = n; i >= 1; --i)
     83             sa[ca[wa[ta[i]]]--] = ta[i];
     84         
     85         rk[sa[1]] = 1;
     86         
     87         for (int i = 2; i <= n; ++i)
     88         {
     89             rk[sa[i]] = rk[sa[i - 1]];
     90             if (wa[sa[i]] != wa[sa[i - 1]]
     91             ||  wb[sa[i]] != wb[sa[i - 1]])
     92                 ++rk[sa[i]];
     93         }
     94     }
     95     
     96     for (int i = 1, j = 0; i <= n; ++i)
     97     {
     98         if (--j < 0)j = 0;
     99         while (s[i + j] == s[sa[rk[i] - 1] + j])++j;
    100         ht[rk[i]] = j;
    101     }
    102 }
    103 
    104 inline int count(int len)
    105 {
    106     int ret = 0, cnt = 1;
    107     
    108     for (int i = 2; i <= n; ++i)
    109         if (ht[i] >= len)
    110             ++cnt;
    111         else
    112         {
    113             if (ret < cnt)
    114                 ret = cnt;
    115             cnt = 1;
    116         }
    117     
    118     if (ret < cnt)
    119         ret = cnt;
    120     
    121     return ret;
    122 }
    123 
    124 signed main(void)
    125 {
    126     n = Int();
    127     m = Int();
    128     
    129     for (int i = 1; i <= n; ++i)
    130         s[i] = map[++tot] = Int();
    131     
    132     std::sort(map + 1, map + tot + 1);
    133     
    134     tot = std::unique(map + 1, map + tot + 1) - map;
    135     
    136     for (int i = 1; i <= n; ++i)
    137         s[i] = std::lower_bound(map + 1, map + tot, s[i]) - map;
    138         
    139     prework_sa();
    140     
    141     int lt = 0, rt = n, mid, ans = 0;
    142     
    143     while (lt <= rt)
    144     {
    145         mid = (lt + rt) >> 1;
    146         
    147         if (count(mid) >= m)
    148             lt = mid + 1, ans = mid;
    149         else
    150             rt = mid - 1;
    151     }
    152     
    153     printf("%d
    ", ans);
    154 }

    @Author: YouSiki

  • 相关阅读:
    nginx模块学习——nginx_http_push_module模块深入讲解和聊天室实现
    常见的qq在线客服代码
    MongoDB数据库介绍及安装(一)
    Python 创建类
    Python backup脚本
    Python 类的初始化小案例
    Python 类实例化
    Python 类初始化__init__
    ObjC(ObjectiveC): NSString应该用initWithFormat? 还是 stringWithFormat?
    NSUserDefaults
  • 原文地址:https://www.cnblogs.com/yousiki/p/6283876.html
Copyright © 2011-2022 走看看