题意
题解
傻逼区间 
  
   DP
   
 反着考虑,就变成每次合并两个相邻字符变成一个新字符。 
 
  
   f[i][j][0..3]
   表示 
  
   [i,j]
   到是否可以合并成某字符。
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int maxn=305;
struct data{
    int m,a[20][2];
} lst[5];
int n;
bool f[maxn][maxn][4];
char a[maxn];
int hhh[300];
int main(){
    memset(hhh,255,sizeof(hhh)); hhh['W']=0; hhh['I']=1; hhh['N']=2; hhh['G']=3; 
    freopen("bzoj1055.in","r",stdin);
    freopen("bzoj1055.out","w",stdout);
    scanf("%d%d%d%d",&lst[0].m,&lst[1].m,&lst[2].m,&lst[3].m);
    for(int k=0;k<=3;k++){
        char s[4];
        for(int i=1;i<=lst[k].m;i++) scanf("%s",s), lst[k].a[i][0]=hhh[s[0]], lst[k].a[i][1]=hhh[s[1]];
    }
    scanf("%s",a+1); n=strlen(a+1);
    for(int i=1;i<=n;i++) if(0<=hhh[a[i]]&&hhh[a[i]]<=3) f[i][i][hhh[a[i]]]=true;
    for(int L=2;L<=n;L++)
     for(int i=1,j=L;j<=n;i++,j++)
      for(int k=0;k<=3;k++){ //f[i][j][k]
        for(int t=i;t<=j-1;t++)
         for(int tt=1;tt<=lst[k].m;tt++) f[i][j][k]|=(f[i][t][lst[k].a[tt][0]]&&f[t+1][j][lst[k].a[tt][1]]);
      }
    bool pd=false;
    if(f[1][n][0]) putchar('W'), pd=true;
    if(f[1][n][1]) putchar('I'), pd=true;
    if(f[1][n][2]) putchar('N'), pd=true;    
    if(f[1][n][3]) putchar('G'), pd=true;
    if(!pd) printf("The name is wrong!");
    return 0;
}
                
                  
                  
                  
                  
                            
                            
本文介绍了一种使用区间动态规划方法解决特定字符合并问题的算法实现。通过反向思考将问题转化为相邻字符的合并操作,并利用三维数组记录可行的合并方案。最终目标是在给定字符串上判断能否通过合并形成特定的目标字符。
          
      
          
                
                
                
                
              
                
                
                
                
                
              
                
                
              
            
                  
					678
					
被折叠的  条评论
		 为什么被折叠?
		 
		 
		
    
  
    
  
            


            