• 【POJ】2778 DNA Sequence(AC自动机+矩阵快速幂)


    题目

    传送门:QWQ

    分析

    对着Trie图搞快速幂。

    为什么这样是对的呢?

    详见:http://www.matrix67.com/blog/archives/276

    有些地方还不是很理解。。。。。。为什么节点还要往下扩展?

    有空再来搞一搞

    代码

     1 //#include <bits/stdc++.h>
     2 #include <cstdio>
     3 #include <algorithm>
     4 #include <cstring>
     5 using namespace std;
     6 typedef long long ll;
     7 const int maxn=200, MOD=100000;
     8 int son[maxn][30], fail[maxn], end[maxn],q[maxn] , newp, flag[maxn];
     9 char s[maxn];
    10 struct Matrix{
    11     ll m[maxn][maxn];
    12     Matrix(){memset(m,0,sizeof(m));}
    13 };
    14 Matrix operator*(const Matrix &mat1,const Matrix &mat2){
    15     Matrix m;
    16     for(int i=1;i<=newp;i++)
    17         for(int j=1;j<=newp;j++)
    18             for(int k=1;k<=newp;k++){
    19                 m.m[i][j]=(m.m[i][j]+mat1.m[i][k]*mat2.m[k][j])%MOD;
    20             }
    21     return m;
    22 }
    23 int find(int cur,int i){
    24     if(!cur) return 1;
    25     if(son[cur][i]) return son[cur][i];
    26     return find(fail[cur],i);
    27 }
    28 int main(){
    29     int n,L;
    30     while(scanf("%d%d",&n,&L)==2){
    31         int l,r;
    32         memset(son,0,sizeof(son)); memset(fail,0,sizeof(fail)); memset(end,0,sizeof(end)); memset(q,0,sizeof(q));
    33         newp=1;
    34         for(int i=1;i<=n;i++){
    35             scanf("%s",s+1);
    36             int cur=1,len=strlen(s+1);
    37             for(int j=1;j<=len;j++){
    38                 if(!son[cur][s[j]-'A']) son[cur][s[j]-'A']=++newp;
    39                 cur=son[cur][s[j]-'A'];
    40             }
    41             end[cur]=i; flag[cur]=1;
    42         }
    43 
    44         Matrix ans,a;
    45         for(q[l=r=1]=1;l<=r;l++){
    46             for(int i=0;i<26;i++){
    47                 if(son[q[l]][i]){ 
    48                     fail[son[q[l]][i]]=find(fail[q[l]],i);
    49                     q[++r]=son[q[l]][i];
    50                 }
    51                 else son[q[l]][i]=find(fail[q[l]],i);
    52                 flag[son[q[l]][i]]|=flag[fail[son[q[l]][i]]];
    53             }
    54         }
    55 
    56         for(int i=1;i<=newp;i++){
    57             if(flag[i]) continue;
    58             for(int j=0;j<26;j++){
    59                 int q=j+'A';
    60                 if(((q=='A'||q=='C'||q=='G'||q=='T'))&&flag[son[i][j]]==0){
    61                     a.m[i][max(son[i][j],1)]++;
    62 
    63                 }
    64             }
    65         }
    66         for(int i=1;i<=newp;i++,puts(""))
    67             for(int j=1;j<=newp;j++){
    68                 printf("%lld ",a.m[i][j]);
    69             }
    70         for(int i=1;i<=newp;i++) ans.m[i][i]=1;
    71         while(L){
    72             if(L&1) ans=ans*a;
    73             a=a*a;
    74             L>>=1;
    75         }
    76         ll res=0;
    77         for(int i=1;i<=newp;i++) res=(res+ans.m[1][i])%MOD;
    78         printf("%d
    ",res);
    79     }
    80 }
    81 /*
    82 5 10
    83 ACGE
    84 CG
    85 CCGG
    86 ACG
    87 TTAC
    88 */
  • 相关阅读:
    golang 给定一个整数数组 nums 和一个目标值 target,请你在该数组中找出和为目标值的那 两个 整数,并返回他们的数组下标。
    BITOP operation destkey key [key ...]
    Viscosity for Mac使用创建您的第一个连接的方法
    ubuntu18没有网络连接Network
    go1.14下Go mod使用实践
    Unity 光照系统
    Unity 单例模式
    Unity 回调函数(Callback)
    Unity 基于OnGUI显示实时FPS
    Unity OnGUI 的可视化编辑
  • 原文地址:https://www.cnblogs.com/noblex/p/9385903.html
Copyright © 2020-2023  润新知