Hdu 2457 DNA repair (ac自己主动机+dp)
题目大意:
改动文本串的上的字符,使之不出现上面出现的串。问最少改动多少个。
思路分析:
dp[i][j]表示如今 i 个字符改变成了字典树上的 j 节点。
然后顺着自己主动机一直转移方程。
注意合法与不合法。
- #include <cstdio>
- #include <iostream>
- #include <cstring>
- #include <algorithm>
- #define inf 0x3f3f3f3f
- using namespace std;
- const char tab = 0;
- const int max_next = 4;
- int idx;
- struct trie
- {
- struct trie *fail;
- struct trie *next[max_next];
- int isword;
- int index;
- trie()
- {
- isword=0;
- memset(next,NULL,sizeof next);
- fail=NULL;
- }
- };
- int rev[256];
- trie *que[100005],ac[100005];
- int head,tail;
- trie *New()
- {
- trie *temp=&ac[idx];
- for(int i=0;i<4;i++)temp->next[i]=NULL;
- temp->fail=NULL;
- temp->isword=0;
- temp->index=idx++;
- return temp;
- }
- void Insert(trie *root,char *word,int len){
- trie *t=root;
- for(int i=0;i<len;i++){
- if(t->next[rev[word[i]]]==NULL)
- t->next[rev[word[i]]]=New();
- t=t->next[rev[word[i]]];
- }
- t->isword++;
- }
- void acbuild(trie *root){
- int head=0,tail=0;
- que[tail++]=root;
- root->fail=NULL;
- while(head<tail){
- trie *temp=que[head++],*p;
- for(int i=0;i<max_next;i++){
- if(temp->next[i]){
- if(temp==root)temp->next[i]->fail=root;
- else {
- p=temp->fail;
- while(p!=NULL){
- if(p->next[i]){
- temp->next[i]->fail=p->next[i];
- break;
- }
- p=p->fail;
- }
- if(p==NULL)temp->next[i]->fail=root;
- }
- if(temp->next[i]->fail->isword)temp->next[i]->isword++;
- que[tail++]=temp->next[i];
- }
- else if(temp==root)temp->next[i]=root;
- else temp->next[i]=temp->fail->next[i];
- }
- }
- }
- void del(trie *root)
- {
- for(int i=0;i<max_next;i++)
- if(root->next[i])del(root->next[i]);
- free(root);
- }
- int dp[2005][2005];
- int solve(char *word,int len)
- {
- memset(dp,0x3f,sizeof dp);
- dp[0][0]=0;
- for(int i=1;i<=len;i++)
- {
- for(int j=0;j<idx;j++)
- {
- if(ac[j].isword)continue;
- if(dp[i-1][j]==inf)continue;
- for(int k=0;k<4;k++)
- {
- int p=ac[j].next[k]->index;
- if(ac[p].isword)continue;
- dp[i][p]=min(dp[i][p],dp[i-1][j]+(k!=rev[word[i-1]]));
- }
- }
- }
- int ans=inf;
- for(int i=0;i<idx;i++)
- ans=min(ans,dp[len][i]);
- return ans==inf?
- -1:ans;
- }
- char word[10005];
- int main()
- {
- rev['A']=0;
- rev['G']=1;
- rev['C']=2;
- rev['T']=3;
- int n,cas=1;
- while(scanf("%d",&n)!=EOF && n)
- {
- idx=0;
- trie *root=New();
- for(int i=1;i<=n;i++)
- {
- scanf("%s",word);
- Insert(root,word,strlen(word));
- }
- acbuild(root);
- scanf("%s",word);
- printf("Case %d: %d\n",cas++,solve(word,strlen(word)));
- }
- return 0;
- }
Hdu 2457 DNA repair (ac自己主动机+dp)的更多相关文章
- POJ 3691 & HDU 2457 DNA repair (AC自己主动机,DP)
http://poj.org/problem?id=3691 http://acm.hdu.edu.cn/showproblem.php?pid=2457 DNA repair Time Limit: ...
- POJ 2778 DNA Sequence (AC自己主动机 + dp)
DNA Sequence 题意:DNA的序列由ACTG四个字母组成,如今给定m个不可行的序列.问随机构成的长度为n的序列中.有多少种序列是可行的(仅仅要包括一个不可行序列便不可行).个数非常大.对10 ...
- HDU - 2825 Wireless Password(AC自己主动机+DP)
Description Liyuan lives in a old apartment. One day, he suddenly found that there was a wireless ne ...
- HDU 2457 DNA repair (AC自动机+DP)
题意:给N个串,一个大串,要求在最小的改变代价下,得到一个不含上述n个串的大串. 思路:dp,f[i][j]代表大串中第i位,AC自动机上第j位的最小代价. #include<algorithm ...
- HDU 2457 DNA repair(AC自动机+DP)题解
题意:给你几个模式串,问你主串最少改几个字符能够使主串不包含模式串 思路:从昨天中午开始研究,研究到现在终于看懂了.既然是多模匹配,我们是要用到AC自动机的.我们把主串放到AC自动机上跑,并保证不出现 ...
- poj 3691 DNA repair(AC自己主动机+dp)
DNA repair Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 5877 Accepted: 2760 Descri ...
- Hdu 3341 Lost's revenge (ac+自己主动机dp+hash)
标题效果: 举个很多种DNA弦,每个字符串值值至1.最后,一个长字符串.要安排你最后一次另一个字符串,使其没事子值和最大. IDEAS: 首先easy我们的想法是想搜索的!管她3721..直接一个字符 ...
- HDU 2825 Wireless Password (AC自己主动机,DP)
pid=2825">http://acm.hdu.edu.cn/showproblem.php? pid=2825 Wireless Password Time Limit: 2000 ...
- HDU 2896 病毒侵袭 (AC自己主动机)
pid=2896">http://acm.hdu.edu.cn/showproblem.php?pid=2896 病毒侵袭 Time Limit: 2000/1000 MS (Java ...
随机推荐
- PHP——面向对象
<body> <?php //类调用用:: //对象调用用-> class Dog1//定义类 { //成员属性(变量) var $name; var $age; var $p ...
- Android基础总结(九)多媒体
多媒体概念(了解) 文字.图片.音频.视频 计算机图片大小的计算(掌握) 图片大小 = 图片的总像素 * 每个像素占用的大小 单色图:每个像素占用1/8个字节 16色图:每个像素占用1/2个字节 25 ...
- js 调试问题
***********06. $(this).index() 失效****************************** 使用的库函数jquery 版本过低,1.4以上即可 ********* ...
- 测试网站访问速度的方法(GTmetrix)
全方位的免费网站速度测试工具 — GTmetrix 它结合了Google Page Speed和Yahoo! YSlow的网页速度测试功能,并且提供可行的建议帮你改善网站速度.会根据网站的具体情况, ...
- when case group by 的用法集合
1.用那个以前大家都熟悉的例子,要求是依旧下面的表格求每个大洲的人口总和 国家(countrcoungry) 人口(population) 中国 600 美国 100 加拿大 100 英国 200 法 ...
- hdu 2857:Mirror and Light(计算几何,点关于直线的对称点,求两线段交点坐标)
Mirror and Light Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) ...
- 如何用ChemDraw选择结构
在使用ChemDraw软件过程中,我们往往会需要对结构进行翻滚.连结.旋转.分解.组合等操作.但是对于新手用户来说不是每种操作大家都会使用的. 针对这种情况我们会有一系列的教程来为大家讲解.下面我们就 ...
- BEGIN_MESSAGE_MAP(Caccess_test_1Dlg, CDialogEx)
BEGIN_MESSAGE_MAP(...消息映射宏的一部分.ON_WM_CREATE()产生一个消息处理函数映射项目,把WM_CREATE和OnCreate函数联系起来. 参数的个数和类型是系统已经 ...
- ionic跳转(二)
1)网上说要想在js里跳转用,$state.go()方法,但找了大半天都没找到在ionic使用$state的方法 2)要想用js跳转,直接用原生js跳转也是可以的 location.href='#ho ...
- Android无线测试之—UiAutomator UiScrollable API介绍四
获取与设置最大滚动次数常量值 一.获取与设置最大滚动次数常量值相关API 返回值 API 描述 int getMaxSearchSwipes() 获取执行搜索滑动过程中的最大滑动次数,默认最大滚动次数 ...