• UVa 1608


    链接:

    https://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=4483

    题意:

    如果一个序列的任意连续子序列中至少有一个只出现一次的元素,则称这个序列是不无聊(non-boring)的。
    输入一个n(n≤200000)个元素的序列A(各个元素均为1e9以内的非负整数),判断它是不是不无聊的。

    分析:

    在整个序列中找一个只出现一次的元素,如果不存在,则这个序列不是不无聊的;
    如果找到一个只出现一次的元素A[k],则只需检查A[1…k-1]和A[k+1…n]是否满足条件(分治)。
    设长度为n的序列需要T(n)时间,则有T(n) = max{T(k-1) + T(n-k) + 找到唯一元素k的时间}。
    如何找唯一元素?如果事先算出每个元素左边和右边最近的相同元素,
    则可以在O(1)时间内判断在任意一个连续子序列中,某个元素是否唯一。
    如果从左边找,最坏情况下唯一元素是最后一个元素,因此
    T(n) = T(n-1) + O(n)≥T(n) = O(n*n)
    从右往左找也一样,只不过最坏情况变成了“唯一元素是第一个元素”,但时间复杂度不变。
    那么,从两边往中间找会怎样?此时T(n) = max{T(k) + T(n-k) + min(k,n-k)},
    而此时的最坏情况是唯一元素在中间的情况,它满足经典递推式T(n) = 2T(n/2) + O(n),即T(n)=O(nlogn)。

    代码:

     1 #include <cstdio>
     2 #include <map>
     3 using namespace std;
     4 
     5 const int UP = 200000 + 5;
     6 int a[UP], prior[UP], after[UP];
     7 
     8 inline bool check(int p, int L, int R){
     9     return prior[p] < L && after[p] > R;
    10 }
    11 
    12 bool judge(int L, int R){
    13     if(L >= R) return true;
    14     for(int d = 0; L + d <= R - d; d++){
    15         if(check(L+d, L, R)) return judge(L, L+d-1) && judge(L+d+1, R);
    16         if(L + d == R - d) break;
    17         if(check(R-d, L, R)) return judge(R-d+1, R) && judge(L, R-d-1);
    18     }
    19     return false;
    20 }
    21 
    22 int main(){
    23     int T, n;
    24     scanf("%d", &T);
    25     while(T--){
    26         map<int,int> M;
    27         scanf("%d", &n);
    28         for(int i = 0; i < n; i++){
    29             scanf("%d", &a[i]);
    30             prior[i] = M.count(a[i]) ? M[a[i]] : -1;
    31             M[a[i]] = i;
    32         }
    33         M.clear();
    34         for(int i = n - 1; i >= 0; i--){
    35             after[i] = M.count(a[i]) ? M[a[i]] : n;
    36             M[a[i]] = i;
    37         }
    38 
    39         if(judge(0, n-1)) printf("non-boring
    ");
    40         else printf("boring
    ");
    41     }
    42     return 0;
    43 }
  • 相关阅读:
    130被围绕的区域
    129求根到叶子节点数字之和
    单表查询
    数据的增删改
    多表结构的创建与分析
    修改表结构
    完整性约束
    基础操作和数据类型
    存储引擎
    Python3.8爬天气网站信息,并保存为CSV(11)
  • 原文地址:https://www.cnblogs.com/hkxy125/p/8310924.html
Copyright © 2020-2023  润新知