码迷,mamicode.com
首页 > 其他好文 > 详细

[Codeforces Round #438][Codeforces 868D. Huge Strings]

时间:2018-09-23 22:40:28      阅读:453      评论:0      收藏:0      [点我收藏+]

标签:pac   amp   哪些   技术分享   can   insert   scan   tmp   test   

题目链接:868D - Huge Strings

题目大意:有\(n\)个字符串,\(m\)次操作,每次操作把两个字符串拼在一起,并询问这个新串的价值。定义一个新串的价值\(k\)为:最大的\(k\),使得这个新串包含所有长度为\(k\)的01串(这样的字符串有\(2^k\)个)

题解:首先来证明对于任何的串,这个\(k\)的值不会超过9

   若\(k=10\),由所有字符串的长度总和不超过100,因此在初始的\(n\)个串里,互不相同的长度为\(k\)的子串不超过100个。又由于每次连接最多能产生9个新的长度为\(k\)的子串(即横跨两个字符串之间的子串),因此互不相同的子串个数最多为\(9 \cdot100+100<2^k\),故\(k<10\)

   接下来就只需要记录每个字符串的前缀,后缀以及长度为\(k\)的子串有哪些就好了。

技术分享图片
#include<bits/stdc++.h>
using namespace std;
#define N 101
int n,m,a,b;
struct rua
{
    string st,ed;
    set<int>has[10];
    bool check(int k)
      {
      for(int i=0;i<(1<<k);i++)
        if(!has[k].count(i))return false;
      return true;
      }
    int ans()
      {
      for(int k=9;k>0;k--)
        if(check(k))return k;
      return 0;
      }
    rua connect(rua nxt)
      {
      rua res=nxt;
      res.st=st;
      if(st.size()<9)
        res.st=st+nxt.st.substr(0,min(nxt.st.size(),9-st.size()));
      int cpy_len=min(ed.size(),9-nxt.ed.size());
      if(nxt.ed.size()<9)
        res.ed=ed.substr(ed.size()-cpy_len,cpy_len)+nxt.ed;
      for(int k=1;k<=9;k++)
        for(auto i:has[k])res.has[k].insert(i);
      string tmp=ed+nxt.st;
      int len=tmp.size();
      for(int i=0;i<len;i++)
        {
        int value=0;
        for(int d=0;d<9 && i+d<len;d++)
          value=value*2+tmp[i+d]-0,
          res.has[d+1].insert(value);
        }
      return res;
      }
}f[2*N];
string s;
int main()
{
    scanf("%d",&n);
    for(int i=1;i<=n;i++)
      {
      cin>>s;
      int len=s.size();
      for(int j=0;j<len;j++)
        {
        int value=0;
        for(int d=0;d<9 && j+d<len;d++)
          value=value*2+s[j+d]-0,
          f[i].has[d+1].insert(value);
        }
      int cpy_len=min(9,len);
      f[i].st=s.substr(0,cpy_len);
      f[i].ed=s.substr(len-cpy_len,cpy_len);
      }
    scanf("%d",&m);
    for(int i=1;i<=m;i++)
      {
      scanf("%d%d",&a,&b);
      f[n+i]=f[a].connect(f[b]);
      printf("%d\n",f[n+i].ans());
      }
}
View Code

 

[Codeforces Round #438][Codeforces 868D. Huge Strings]

标签:pac   amp   哪些   技术分享   can   insert   scan   tmp   test   

原文地址:https://www.cnblogs.com/DeaphetS/p/9693580.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!