题意:容易理解...

分析:在做这道题之前我做了hdu 4057,都是同一种类型的题,因为题中给的模式串的个数最多只能为10个,所以我们就很容易想到用状态压缩来做,但是开始的时候我的代码超时了dp时我们由dp[i][j][k]枚举其后接的字符转移到dp[i+1],在枚举前判断下是否有dp[i][j][k]=0,是的话可以直接continue,而不用再深一层循环.这样优化之后就没超时了。我用了滚动数组实现,其实这题可以不用滚动数组也可以过的,空间上不会卡。

代码实现:

  1. #include<cstdio>
  2. #include<cstring>
  3. #include<cstdlib>
  4. #include<iostream>
  5. #include<queue>
  6. #include<cmath>
  7. #include<algorithm>
  8. using namespace std;
  9. struct node{
  10. int next[];
  11. int fail;
  12. int flag;
  13. void init()
  14. {
  15. memset(next,,sizeof(next));
  16. fail=;
  17. flag=;
  18. }
  19. }a[];
  20. char keyword[];
  21. int tot,n,m,len;
  22. int dp[][][<<];
  23.  
  24. void chushihua()
  25. {
  26. tot=;
  27. a[].init();
  28. memset(dp,,sizeof(dp));
  29. }
  30.  
  31. void insert(char *str,int biaohao)
  32. {
  33. int index,p=;
  34. for(;*str!='\0';str++)
  35. {
  36. index=*str-'a';
  37. if(a[p].next[index]==)
  38. {
  39. a[++tot].init();
  40. a[p].next[index]=tot;
  41. }
  42. p=a[p].next[index];
  43. }
  44. a[p].flag=a[p].flag|(<<biaohao);
  45. }
  46.  
  47. void build_fail()
  48. {
  49. queue<int>Q;
  50. int cur,p,son,i;
  51. Q.push();
  52. while(!Q.empty())
  53. {
  54. p=Q.front();
  55. Q.pop();
  56. for(i=;i<;i++)
  57. {
  58. if(a[p].next[i]!=)
  59. {
  60. son=a[p].next[i];
  61. cur=a[p].fail;
  62. if(p==)
  63. a[son].fail=;
  64. else
  65. {
  66. // while(cur&&a[cur].next[i]==0)
  67. // cur=a[cur].fail;
  68. a[son].fail=a[cur].next[i];
  69. }
  70. a[son].flag=a[son].flag|a[a[son].fail].flag;
  71. Q.push(son);
  72. }
  73. else
  74. a[p].next[i]=a[a[p].fail].next[i];
  75. }
  76. }
  77. }
  78.  
  79. int panduan(int x)
  80. {
  81. int i,s=;
  82. for(;x;x=x>>)
  83. if(x&)
  84. s++;
  85. if(s>=m)
  86. return ;
  87. else
  88. return ;
  89. }
  90.  
  91. void solve()
  92. {
  93. int i,j,k,l,son,sum=,temp;
  94. dp[][][]=;
  95. for(i=;i<=len;i++)
  96. {
  97. memset(dp[&i],,sizeof(dp[&i]));//滚动数组
  98. for(j=;j<=tot;j++)
  99. for(l=;l<(<<);l++)
  100. {
  101. if(dp[&(i+)][j][l]==)//开始这里没加,果断超时了
  102. continue;
  103. for(k=;k<;k++)//开始的时候这层for循环和上一层for循环调换过来的,没有加那个if判断,导致超时了
  104. {
  105. son=a[j].next[k];
  106. temp=l|a[son].flag;
  107. dp[&i][son][temp]+=dp[&(i+)][j][l];
  108. if(dp[&i][son][temp]>=)
  109. dp[&i][son][temp]%=;
  110. }
  111. }
  112. }
  113. for(i=;i<=tot;i++)
  114. for(j=;j<(<<);j++)
  115. {
  116. if(panduan(j))
  117. sum=sum+dp[&len][i][j];
  118. if(sum>=)
  119. sum%=;
  120. }
  121. printf("%d\n",sum);
  122. }
  123.  
  124. int main()
  125. {
  126. int i;
  127. while(scanf("%d%d%d",&len,&n,&m)!=EOF&&(len+n+m)!=)
  128. {
  129. chushihua();
  130. getchar();
  131. for(i=;i<n;i++)
  132. {
  133. scanf("%s",keyword);
  134. insert(keyword,i);
  135. }
  136. build_fail();
  137. solve();
  138. }
  139. return ;
  140. }

hdu 2825(ac自动机+状态压缩dp)的更多相关文章

  1. HDU 4511 (AC自动机+状态压缩DP)

    题目链接:  http://acm.hdu.edu.cn/showproblem.php?pid=4511 题目大意:从1走到N,中间可以选择性经过某些点,比如1->N,或1->2-> ...

  2. hdu 4057(ac自动机+状态压缩dp)

    题意:容易理解... 分析:题目中给的模式串的个数最多为10个,于是想到用状态压缩dp来做,它的状态范围为1-2^9,所以最大为2^10-1,那我们可以用:dp[i][j][k]表示长度为i,在tri ...

  3. hdu 2825 aC自动机+状压dp

    Wireless Password Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others ...

  4. POJ 3691 (AC自动机+状态压缩DP)

    题目链接:  http://poj.org/problem?id=3691 题目大意:给定N个致病DNA片段以及一个最终DNA片段.问最终DNA片段最少修改多少个字符,使得不包含任一致病DNA. 解题 ...

  5. bzoj1195 神奇的ac自动机+状态压缩dp

    /* 难的不是ac自动机,是状态压缩dp 之前做了一两题类似题目,感觉理解的还不够透彻 */ #include<iostream> #include<cstdio> #incl ...

  6. HDU 4057 Rescue the Rabbit ( AC自动机 + 状态压缩DP )

    模板来自notonlysuccess. 模式串只有10个,并且重复出现的分值不累加,因此很容易想到状态压缩. 将模式串加入AC自动机,最多有10*100个状态. dp[i][j][k]:串长为i,在T ...

  7. HDU 4758 Walk Through Squares( AC自动机 + 状态压缩DP )

    题意:给你两个串A,B, 问一个串长为M+N且包含A和B且恰好包含M个R的字符串有多少种组合方式,所有字符串中均只含有字符L和R. dp[i][j][k][S]表示串长为i,有j个R,在自动机中的状态 ...

  8. 计蒜客-蒜场抽奖(AC自动机+状态压缩DP)

    题解:题意不再说了,题目很清楚的. 思路:因为N<=10,所以考虑状态压缩 AC自动机中 val[1<<i]: 表示第i个字符串.AC自动机中fail指针是指当前后缀在其他串里面所能 ...

  9. hdu 3341(ac自动机+状态压缩)

    题意:容易理解... 思路:首先一开始容易想到要用到dp,开设一个dp[41][41][41][41][501]的数组来解决,但是明显内存已经超出范围了,于是就想如何减少内存呢?只要知道A.T.C.G ...

随机推荐

  1. ubuntu下安装spark1.4.0

    构建在hadoop2.6.0之上的 1.在官网下载spark-1.4.0-bin-hadoop2.6.tgz 2.解压到你想要放的文件夹里,tar zxvf spark-1.4.0-bin-hadoo ...

  2. Struts2 常用的常量配置

    在struts2-core-2.1.8.1.jar的org.apache.struts2包下面的default.properties资源文件里可以查到常用的常量配置,这些不用刻意的记住:忘记的时候可以 ...

  3. Oracle 9 - 分析undo和snapshot too old错误

    什么操作会生成undo INSERT生成的UNDO最少,只要记录新的rowid UPDATE生成的undo多一点,它要记录修改前的数据中的那部分. DELETE生成最多的undo, 因为它要记录整行被 ...

  4. Netty 的Downstream 和 Upstream

    Netty的Downstream 和 Upstream 如果一个event从第一个handler传递直到最后一个handler就是 Upstream 相反的如果一个event从最后一个handler传 ...

  5. Python图片转换成矩阵,矩阵数据转换成图片

    # coding=gbk from PIL import Image import numpy as np # import scipy def loadImage(): # 读取图片 im = Im ...

  6. Android:简单联网获取网页代码

    设置权限,在AndroidManifest.xml加入 <uses-permission android:name="android.permission.INTERNET" ...

  7. Android:创建Android工程

    创建Android工程,在Eclipse左栏右键 new->project..   (版本不一样,名字会有所区别) 然后选择Android下的Android application projec ...

  8. *IDEA真好用

    使用maven做开发,在编辑pom.xml文件时

  9. SQL索引一步到位(此文章为“数据库性能优化二:数据库表优化”附属文章之一)

    SQL索引一步到位(此文章为“数据库性能优化二:数据库表优化”附属文章之一) SQL索引在数据库优化中占有一个非常大的比例, 一个好的索引的设计,可以让你的效率提高几十甚至几百倍,在这里将带你一步步揭 ...

  10. long和Long的区别

    Java中数据类型分两种:1.基本类型:long,int,byte,float,double2.对象类型:Long,Integer,Byte,Float,Double其它一切java提供的,或者你自己 ...