HDOJ 4057 - Rescue the Rabbit 简单的AC自动机+状态压缩DP
来源:互联网 发布:java 网络通信框架 编辑:程序博客网 时间:2024/04/29 12:38
题意:
众所周知..DNA序列由"A","G","T","C"组成....
现在N个DNA序列(每个长度没说..假设都小于1000吧...1<=N<=10)...并且告诉每个DNA序列能得到的分数Wi,(|Wi|<=100)...
若一个DNA串包含其中的某些串..那么得分就是包括的串分数之和(一个串不管出现了多少次..只算一次)..
问..若构造长度为M(1<=M<=100)的DNA序列...能得到的最大分数为多少...
题解:
裸AC自动机...然后10个DNA子串...状态压缩DP...复杂度有些高 100*1000*1024*4...好久没写AC自动机了..差点写跪....再一个写程序的时候memset最好直接用for循环去代替吧..常数比较大....
Program:
#include<iostream>#include<stdio.h>#include<cmath>#include<queue>#include<algorithm>#include<string.h>#define MAXN 10002using namespace std;struct node{ int son[4],fail,w;}P[MAXN];char s[1005];bool dp[2][1015][1<<10];int val[1<<10],turn[30],num;void initial(int h){ int x; for (x=0;x<4;x++) P[h].son[x]=0; P[h].fail=P[h].w=0;}void Built_Trie(int n){ int h,k,t,x,i,y,len; initial(0),num=0; for (t=0;t<n;t++) { scanf("%s%d",s+1,&val[t]),len=strlen(s+1); if (len>100) { val[t]=0; continue; } h=0; for (i=1;i<=len;i++) { x=turn[s[i]-'A']; if (!P[h].son[x]) P[h].son[x]=++num,initial(num); h=P[h].son[x]; } P[h].w|=1<<t; }}void Built_AC(){ int h,k,x; queue<int> Q; while (Q.size()) Q.pop(); for (x=0;x<4;x++) if (P[0].son[x]) Q.push(P[0].son[x]); while (Q.size()) { h=Q.front(),Q.pop(); for (x=0;x<4;x++) { k=P[h].fail; while (k && !P[k].son[x]) k=P[k].fail; P[P[h].son[x]].fail=P[k].son[x]; if (!P[h].son[x]) P[h].son[x]=P[k].son[x]; else { Q.push(P[h].son[x]); k=P[h].fail; while (1) { P[P[h].son[x]].w|=P[P[k].son[x]].w,k=P[k].fail; if (!k) break; } } } }}int AC_DP(int n,int L){ int l,w,h,x,h1,w1,temp,ans=-1,g=0; memset(dp,false,sizeof(dp)); dp[g][0][0]=true; for (l=1;l<=L;l++) { g=1-g; for (h=0;h<=num;h++) for (w=0;w<(1<<n);w++) dp[g][h][w]=false; for (h=0;h<=num;h++) for (w=0;w<(1<<n);w++) if (dp[1-g][h][w]) for (x=0;x<4;x++) { h1=P[h].son[x]; w1=w|P[h1].w; dp[g][h1][w1]=true; } } for (h=0;h<=num;h++) for (w=0;w<(1<<n);w++) if (dp[g][h][w]) dp[g][0][w]=true; for (w=0;w<(1<<n);w++) if (dp[g][0][w]) { temp=0; for (x=0;x<n;x++) if (w & 1<<x) temp+=val[x]; ans=max(ans,temp); } return ans;}int main(){ int n,l,ans; turn['A'-'A']=0,turn['G'-'A']=1, turn['T'-'A']=2,turn['C'-'A']=3; while (~scanf("%d%d",&n,&l)) { Built_Trie(n); Built_AC(); ans=AC_DP(n,l); if (ans<0) puts("No Rabbit after 2012!"); else printf("%d\n",ans); } return 0;}
- HDOJ 4057 - Rescue the Rabbit 简单的AC自动机+状态压缩DP
- hdu4057 Rescue the Rabbit,AC自动机,状态压缩dp
- HDU 4057 Rescue the Rabbit(11年大连,AC自动机+状态压缩DP)
- Hdu 4057 Rescue the Rabbit (AC自动机+状态压缩dp) - 2011 ACM-ICPC Dalian Regional Contest Problem G
- ZOJ3545---Rescue the Rabbit(AC自动机+dp)
- hdu 4057 Rescue the Rabbit AC自动机+DP
- HDU 4057 Rescue the Rabbit (AC自动机+DP)
- HDU 4057 Rescue the Rabbit 【AC自动机+状压DP】
- hdu4057 Rescue the Rabbit(AC自动机+DP)
- Zoj 3545 Rescue the Rabbit(ac自动机+dp)
- zoj 3545 - Rescue the Rabbit(AC自动机+dp)
- hdu4057 Rescue the Rabbit【AC自动机+dp滚动数组】
- 2011 Asia Dalian Regional Contest _ Rescue the Rabbit AC自动机+状压DP
- ZOJ 3545 Rescue the Rabbit AC自动机 + DP (2011大连区域赛G题)
- hdu 4057 AC自动机+状态压缩dp
- HDU 3247 AC自动机 + 状态压缩dp
- HDU 4534(ac自动机+状态压缩dp)
- hdu 2825 ac自动机+状态压缩dp
- RTSP协议、SPDY协议
- Android中的BroadcastReceiver理解
- Spring核心原理:依赖注入Dependency Injection(控制反转Inversion of Control)
- COM组件
- Linux网络编程 之 UDP 单播
- HDOJ 4057 - Rescue the Rabbit 简单的AC自动机+状态压缩DP
- android 图片加文字
- 你若不甘,策马扬鞭!
- android-SQLite数据库总结
- 一个简单的计算器
- Linux 删除和替换文件中某一行的方法
- Android EditText 文本框实现搜索和清空效果
- jQuery控制字体大小
- linux shell 数值运算