题目链接:传送门
题解:
用f[l][r][i]表示从l到r能否合成第i种字符,转移很好写
//by sdfzchy
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
typedef long long LL;
const int inf=(1<<30),N=100010,mod=1e9+7;
int n,cnt[5];
inline int in()
{
char tmp=getchar();
int res=0,f=1;
while((tmp<'0'||tmp>'9')&&tmp!='-')tmp=getchar();
if(tmp=='-') f=-1,tmp=getchar();
while(tmp>='0'&&tmp<='9') res=(res<<1)+(res<<3)+(tmp^48),tmp=getchar();
return res*f;
}
bool f[210][210][5];
bool ha[5][5][5];
int id(char c)
{
if(c=='W') return 1;
if(c=='I') return 2;
if(c=='N') return 3;
if(c=='G') return 4;
}
void put(int i)
{
if(i==1) putchar('W');
if(i==2) putchar('I');
if(i==3) putchar('N');
if(i==4) putchar('G');
}
char s[1010];
int main()
{
char ss[100];
for(int i=1;i<=4;i++) cnt[i]=in();
for(int i=1;i<=4;i++)
for(int j=1;j<=cnt[i];j++)
{
scanf("%s",ss);
ha[id(ss[0])][id(ss[1])][i]=1;
}
scanf("%s",s+1);
n=strlen(s+1);
for(int i=1;i<=n;i++) f[i][i][id(s[i])]=1;
for(int i=1;i<n;i++)
for(int l=1,r=i+l;l<=n-i;l++,r++)
for(int j=1;j<=4;j++)
if(!f[l][r][j])
for(int x=1;x<=4;x++)
for(int y=1;y<=4;y++)
if(ha[x][y][j])
for(int k=l;k<r;k++)
f[l][r][j]|=(f[l][k][x]&f[k+1][r][y]);
bool ok=0;
for(int i=1;i<=4;i++)
if(f[1][n][i])
put(i),ok=1;
if(!ok) puts("The name is wrong!");
return 0;
}