codeforce469DIV2——C. Zebras

题意

0, 010, 01010 这一类的01交替且开头和结尾都为0的序列被称为zebra序列。给出一段01序列,尝试能否把他分为k个子序列使得每个子序列都是zebra序列。

分析

这个题应该算是水题把,但是确实把我卡了。

一开始暴力找在序列中找1,然后分别往前往后各找一个0。但是最坏情况到O(n^2),TLE在第八组。然后我尝试了各种Set,vector,二分之类的瞎搞结果一直都没把复杂度降下来一直T在第八组绝望了。

赛后看其他人的代码发现··可以O(n)扫一遍,当s[i]是0的时候找加入最后一个是1的方案,若是1则加入最后一个是0的方案。如果没有合适的方案,就新开一个。可以用优先队列或者set搞

 

 1 #include <cstdio>
 2 #include <algorithm>
 3 #include <cstring>
 4 #include <iostream>
 5 #include <queue>
 6 #include <vector>
 7 using namespace std;
 8 const int maxn=200000+10;
 9 char s[maxn];
10 priority_queue<int,vector<int>,greater<int> >q0,q1;
11 vector<int>Q[maxn];
12 int n,p;
13 int main(){
14     scanf("%s",s+1);
15     n=strlen(s+1);
16     p=0;
17     bool ok=1;
18     for(int i=1;i<=n;i++){
19         if(s[i]=='1'){
20             if(q0.empty()){
21                 ok=0;
22                 break;
23             }
24             int tmp=q0.top();
25             q0.pop();
26             Q[tmp].push_back(i);
27             q1.push(tmp);
28         }else{
29             if(q1.empty()){
30                 p++;
31                 Q[p].push_back(i);
32                 q0.push(p);
33             }else{
34                 int tmp=q1.top();
35                 q1.pop();
36                 Q[tmp].push_back(i);
37                 q0.push(tmp);
38             }
39         }
40     }
41     if(!ok||!q1.empty()){
42         printf("-1");
43         return 0;
44     }
45     printf("%d\n",p);
46     for(int i=1;i<=p;i++){
47         printf("%d ",Q[i].size());
48         for(int j=0;j<Q[i].size();j++)
49             printf("%d ",Q[i][j]);
50         printf("\n");
51     }
52 return 0;
53 }
View Code

 

posted @ 2018-04-10 23:42  蒟蒻LQL  阅读(200)  评论(0编辑  收藏  举报