题意:有m种DNA序列是有疾病的,问有多少种长度为n的DNA序列不包含任何一种有疾病的DNA序列。(仅含A,T,C,G四个字符)

解题关键:AC自动机,实际上就是一个状态转移图,注意能少取模就少取模,尤其是在快速幂的时候,消耗时间极其巨大,此题效率差10倍。

先+=在进行取模,两者分开,也可以快1倍。

按照AC自动机建立邻接矩阵,其中不含病毒模式串的位置可以到达,

其中上图矩阵为:

2 1 0 0 1

2 1 1 0 0

1 1 0 1 1

2 1 0 0 1

2 1 0 0 1

去掉病毒结点之后,变为

2 1

2 1

转移方程:$dp[u] = \sum\limits_{v -  > u} {dp[v]} $

 #include<cstdio>
#include<cstring>
#include<algorithm>
#include<cstdlib>
#include<cstring>
#include<iostream>
#include<queue>
using namespace std;
typedef long long ll;
const int N=;
const int MAXN=;
struct mat{
ll m[][];
};
ll m,n;
ll mod=;
struct Trie{
int Next[MAXN][N],Fail[MAXN],root,tot;
bool End[MAXN];
int newnode(){
for(int i=;i<N;i++) Next[tot][i]=-;
End[tot++]=false;
return tot-;
}
void init(){
tot=;
root=newnode();
}
void insert(char buf[]){
int len=strlen(buf),now=root,k;
for(int i=;i<len;i++){
if(buf[i]=='A') k=;
else if(buf[i]=='G') k=;
else if(buf[i]=='C') k=;
else k=;
if(Next[now][k]==-) Next[now][k]=newnode();
now=Next[now][k];
}
End[now]=true;
}
void build(){
queue<int>que;
Fail[root]=root;
for(int i=;i<N;i++){
if(Next[root][i]==-) Next[root][i]=root;
else{
Fail[Next[root][i]]=root;
que.push(Next[root][i]);
}
}
while(!que.empty()){
int now=que.front();
que.pop();
if(End[Fail[now]]) End[now]=true;
for(int i=;i<N;i++){
if(Next[now][i]==-) Next[now][i]=Next[Fail[now]][i];
else{
Fail[Next[now][i]]=Next[Fail[now]][i];
que.push(Next[now][i]);
}
}
}
}
mat get_mat(int len){
mat B={};
for(int i=;i<len;i++){
for(int j=;j<N;j++){
if(End[Next[i][j]]==false) B.m[i][Next[i][j]]++;//不能直接置1
}
}
return B;
}
}; mat mul(mat &A,mat &B,int len){
mat C={};
for(int i=;i<len;i++){
for(int j=;j<len;j++){
for(int k=;k<len;k++){
C.m[i][j]+=A.m[i][k]*B.m[k][j];
}
C.m[i][j]%=mod;
}
}
return C;
} mat pow(mat A,ll n,int len){
mat B={};
for(int i=;i<len;i++) B.m[i][i]=;
while(n){
if(n&) B=mul(B,A,len);
A=mul(A,A,len);
n>>=;
}
return B;
} Trie ac;
char buf[];
int main(){
while(scanf("%lld%lld",&m,&n)!=EOF){
ac.init();
for(int i=;i<m;i++){
scanf("%s",buf);
ac.insert(buf);
}
ac.build();
mat B=ac.get_mat(ac.tot);
B=pow(B,n,ac.tot);
ll res=;
for(int i=;i<ac.tot;i++){
res+=B.m[][i];
}
printf("%lld\n",res%mod);
}
return ;
}

[poj2778]DNA Sequence(AC自动机+矩阵快速幂)的更多相关文章

  1. poj2778 DNA Sequence(AC自动机+矩阵快速幂)

    Description It's well known that DNA Sequence is a sequence only contains A, C, T and G, and it's ve ...

  2. poj 2778 DNA Sequence ac自动机+矩阵快速幂

    链接:http://poj.org/problem?id=2778 题意:给定不超过10串,每串长度不超过10的灾难基因:问在之后给定的长度不超过2e9的基因长度中不包含灾难基因的基因有多少中? DN ...

  3. poj2778DNA Sequence (AC自动机+矩阵快速幂)

    转载请注明出处: http://www.cnblogs.com/fraud/          ——by fraud DNA Sequence Time Limit: 1000MS   Memory ...

  4. POJ2778 DNA Sequence(AC自动机 矩阵)

    先使用AC自动机求得状态转移关系,再建立矩阵,mat[i][j]表示一步可从i到j且i,j节点均非终止字符的方案数,则此矩阵的n次方表示n步从i,到j的方法数. #include<cstdio& ...

  5. POJ2778 DNA Sequence(AC自动机+矩阵快速幂)

    题目给m个病毒串,问不包含病毒串的长度n的DNA片段有几个. 感觉这题好神,看了好久的题解. 所有病毒串构造一个AC自动机,这个AC自动机可以看作一张有向图,图上的每个顶点就是Trie树上的结点,每个 ...

  6. POJ 2778 DNA Sequence (ac自动机+矩阵快速幂)

    DNA Sequence Description It's well known that DNA Sequence is a sequence only contains A, C, T and G ...

  7. DNA Sequence POJ - 2778 AC自动机 && 矩阵快速幂

    It's well known that DNA Sequence is a sequence only contains A, C, T and G, and it's very useful to ...

  8. POJ 2778 DNA Sequence(AC自动机 + 矩阵快速幂)题解

    题意:给出m个模式串,要求你构造长度为n(n <= 2000000000)的主串,主串不包含模式串,问这样的主串有几个 思路:因为要不包含模式串,显然又是ac自动机.因为n很大,所以用dp不太好 ...

  9. POJ2778(SummerTrainingDay10-B AC自动机+矩阵快速幂)

    DNA Sequence Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 17160   Accepted: 6616 Des ...

随机推荐

  1. 【C语言】求两个数中不同的位的个数

    //求两个数中不同的位的个数 #include <stdio.h> int count_different(int a, int b) { int count = 0; int c = a ...

  2. .Net 平台WebService的创建、部署和使用介绍

    .NET平台内建了对Web Service的支持,包括Web Service的构建和使用.与其它开发平台不同,使用.NET平台,你不需要其他的工具或者SDK就可以完成Web Service的开发了.. ...

  3. C---指针篇

    指针变量:专门存放内存地址的一种变量 听说C因为指针而强大 一段代码来解释 指针 *指针 &指针 &指向变量 的关系 /* * 返回指针所指向内存地址中存放的值 它是单目运算符 也称作 ...

  4. 何时使用Entity或DTO

    关注公众号: 锅外的大佬 每日推送国外优秀的技术翻译文章,励志帮助国内的开发者更好地成长! JPA和Hibernate允许你在JPQL和Criteria查询中使用DTO和Entity作为映射.当我在我 ...

  5. Scrapy爬虫入门系列1 安装

    安装python2.7 参见CentOS升级python 2.6到2.7 安装pip 参见CentOS安装python setuptools and pip‎ 依赖 https://docs.scra ...

  6. android arcmenu

    http://www.kankanews.com/ICkengine/archives/129193.shtml

  7. MVC入门——删除页

    添加Action DeleteUserInfo using System; using System.Collections.Generic; using System.Linq; using Sys ...

  8. flume采集微信小程序数据

    flume采集微信小程序数据 flume收集前端埋点数据[1]POST请求http://f.x.com:50000数据格式: JsonArray数据格式示例:[{ "headers" ...

  9. pyinstaller-py2exe-cx_Freeze打包第一个wxPython程序HelloWorld

    pyinstaller 打包hello 7Mb ================= www.pyinstaller.org pip install pypiwin32 pip install pyin ...

  10. 剑指Offer:树的子结构【26】

    剑指Offer:树的子结构[26] 题目描述 输入两棵二叉树A,B,判断B是不是A的子结构.(ps:我们约定空树不是任意一个树的子结构) 解题思路 分为两步: 第一步:在树A中找到和树B的根节点的值一 ...