【字符串+BFS】Problem 7. James Bond

https://www.bnuoj.com/v3/external/gym/101241.pdf

【题意】

  • 给定n个字符串,大小写敏感
  • 定义一个操作:选择任意m个串首尾相连组成一个新串
  • 问是否存在一个这样的串s,s可以由不同的串首尾相连得到
  • 最多100个字符串,所有字符串的总长度不超过5000

【样例解释】

aB5可以由a+B5得到,也可以由aB+5得到,所以输出YES

【思路】

  • 首先一定是在100个选择2个串a,b,a是b的前缀
  • 然后a和b的前缀可以消去,我们想知道b剩下的右半部分是哪一个串的前缀
  • 找到这个串后前缀也可以消去,然后再找剩下的部分
  • 因为数据范围不是很大,所以可以暴力搜索,bfs 700ms过
  • vis[i][j]在bfs中去重,代表是i字符串的以j开始的后缀

【AC】

  1 #include<iostream>
  2 #include<cstdio>
  3 #include<cstring>
  4 #include<cmath>
  5 #include<algorithm>
  6 #include<queue>
  7 
  8 using namespace std;
  9 int n;
 10 const int maxn=5e4+2;
 11 char str[102][maxn];
 12 int len[102];
 13 int flag;
 14 bool vis[102][maxn];
 15 struct node
 16 {
 17     int id;
 18     int len;
 19     node(){}
 20     node(int _id,int _len):id(_id),len(_len){}
 21 };
 22 bool solve()
 23 {
 24     queue<node> Q;
 25     for(int i=0;i<n;i++)
 26     {
 27         for(int j=0;j<i;j++)
 28         {
 29             int l=min(len[i],len[j]);
 30             int tot=0;
 31             for(int k=0;k<l;k++)
 32             {
 33                 if(str[i][k]==str[j][k]) tot++;
 34                 else break;
 35             }
 36             if(tot!=l) continue;
 37             if(len[i]==len[j]) return true;
 38             if(len[i]<len[j]) 
 39             {
 40                 vis[j][len[i]]=true;
 41                 Q.push(node(j,len[i]));
 42             }
 43             else
 44             {
 45                 vis[i][len[j]]=true;
 46                 Q.push(node(i,len[j]));
 47             }
 48         }
 49     }
 50     while(!Q.empty())
 51     {
 52         node q=Q.front(); Q.pop();
 53         for(int i=0;i<n;i++)
 54         {
 55             int lq=len[q.id]-q.len;
 56             int l=min(lq,len[i]);
 57             int tot=0;
 58             for(int j=0;j<l;j++)
 59             {
 60                 if(str[i][j]==str[q.id][q.len+j]) tot++;
 61                 else break;
 62                 if(tot==l)
 63                 {
 64                     if(lq==len[i]) return true;
 65                     else if(lq<len[i])
 66                     {
 67                         if(!vis[i][lq])
 68                         {
 69                             vis[i][lq]=true;
 70                             Q.push(node(i,lq));
 71                         }
 72                     }
 73                     else 
 74                     {
 75                         if(!vis[q.id][q.len+len[i]])
 76                         {
 77                             vis[q.id][q.len+len[i]]=true;
 78                             Q.push(node(q.id,q.len+len[i]));
 79                         }
 80                     }
 81 
 82                 }
 83             }
 84         }
 85     }
 86     return false;
 87 }
 88 int main()
 89 {
 90     freopen("input.txt","r",stdin);
 91     freopen("output.txt","w",stdout);
 92     scanf("%d",&n);
 93     for(int i=0;i<n;i++)
 94     {
 95         scanf("%s",str[i]);
 96         len[i]=strlen(str[i]);
 97     }
 98     if(solve())
 99     {
100         puts("YES");
101     }
102     else
103     {
104         puts("NO");
105     }
106     return 0;
107 }
View Code

 

posted @ 2017-08-15 21:54  shulin15  阅读(245)  评论(0编辑  收藏  举报