HDU 4534
来源:互联网 发布:java中高级笔试面试题 编辑:程序博客网 时间:2024/06/16 19:27
AC自动机水题,想清楚状态表示即可。
我一开始多设计一维状态记录之前用了多少个删除操作,MLE,其实这个状态不需要记录的,作为一个待求最值的变量。
#include <cstdio>#include <cstring>#include <algorithm>#include <queue>#define N 1700using namespace std;const int INF=-((~(0U))>>1);char s[110];int score;int next[N][26],pos,flag[N],sta[N],val[N],fail[N],tot;int newnode(){ memset(next[pos],0,sizeof(next[pos])); flag[pos]=fail[pos]=sta[pos]=val[pos]=0; return pos++;}void insert(char * s,int score){ int p=0,i; for(i=0;s[i];i++){ int k=s[i]-'a'; p=next[p][k]?next[p][k]:next[p][k]=newnode(); } if(score==999){ flag[p]=1; sta[p]=(1<<tot); tot++; } else if(score==-999){ flag[p]=-1; } else{ flag[p]=2; val[p]=score; }}void makefail(){ queue<int>q; q.push(0); int i,p=0; while(!q.empty()){ int u=q.front(); q.pop(); for(i=0;i<26;i++){ int v=next[u][i]; if(v==0) next[u][i]=next[fail[u]][i]; else q.push(v); if(u&&v){ fail[v]=next[fail[u]][i]; if(flag[fail[v]]==-1){ flag[v]=-1; } else if(flag[v]!=-1){ sta[v]|=sta[fail[v]]; val[v]+=val[fail[v]]; } } } }}int dp[2][260][N];int cost[2][260][N];void makeans(){ int i,j,k,len,cur; len=strlen(s); cur=1; for(j=0;j<(1<<tot);j++) for(k=0;k<pos;k++) dp[0][j][k]=-INF,cost[0][j][k]=INF; dp[0][0][0]=0; cost[0][0][0]=0; for(i=0;s[i];i++){ for(j=0;j<(1<<tot);j++) for(k=0;k<pos;k++) dp[cur][j][k]=-INF,cost[cur][j][k]=INF; for(j=0;j<(1<<tot);j++){ for(k=0;k<pos;k++){ if(dp[cur^1][j][k]==-INF)continue; if(dp[cur][j][k]>dp[cur^1][j][k]+1){ dp[cur][j][k]=dp[cur^1][j][k]+1; cost[cur][j][k]=cost[cur^1][j][k]; } else if(dp[cur][j][k]==dp[cur^1][j][k]+1){ cost[cur][j][k]=max(cost[cur][j][k],cost[cur^1][j][k]); } } } for(j=0;j<(1<<tot);j++){ for(k=0;k<pos;k++){ if(dp[cur^1][j][k]==-INF)continue; int v=next[k][s[i]-'a']; if(flag[v]==-1)continue; //if((j|sta[v])==((1<<tot)-1)) printf("***%d %d %d %d\n",i,j,k,p); if(dp[cur][j|sta[v]][v]>dp[cur^1][j][k]){ dp[cur][j|sta[v]][v]=dp[cur^1][j][k]; cost[cur][j|sta[v]][v]=cost[cur^1][j][k]+val[v]; } else if(dp[cur][j|sta[v]][v]==dp[cur^1][j][k]){ cost[cur][j|sta[v]][v]=max(cost[cur][j|sta[v]][v],cost[cur^1][j][k]+val[v]); } } } cur^=1; } int ans1=-INF; int ans=INF; for(j=0;j<pos;j++){ if(dp[cur^1][(1<<tot)-1][j]<ans1){ ans1=dp[cur^1][(1<<tot)-1][j]; ans=cost[cur^1][(1<<tot)-1][j]; } else if(dp[cur^1][(1<<tot)-1][j]==ans1){ ans=max(ans,cost[cur^1][(1<<tot)-1][j]); } } if(ans1!=-INF){ printf("%d %d\n",ans1,ans); return ; } printf("Banned\n");}int main(){ int t,T,n,i,j; scanf("%d",&T); for(t=1;t<=T;t++){ scanf("%d",&n); pos=0,newnode(); tot=0; for(i=1;i<=n;i++){ scanf("%s %d",s,&score); insert(s,score); } makefail(); scanf("%s",s); printf("Case %d: ",t); makeans(); } return 0;}
- HDU 4534
- hdu
- hdu
- HDU
- hdu ()
- hdu
- hdu
- HDU
- HDU
- hdu
- hdu
- HDU
- Hdu
- hdu
- hdu-
- hdu
- hdu
- hdu
- 日语的音读与训读
- 自己用php写的乘法口诀表
- 解决NDK出现error: exception handling disabled, use -fexceptions to enable的问题
- java.util.concurrent介绍
- ubuntu 12.04下gdm gnome的安装简介
- HDU 4534
- Java byte[]和short[]之间的相互转换
- java socket学习实例
- HDOj 2094 产生冠军(拓扑排序)
- java socket学习
- Gridview的RowDataBound事件可以做很多事情
- nginx源码分析—队列结构ngx_queue_t
- POJ 2585 Window Pains (拓扑排序)
- 根据年月日算出是星期几