BZOJ1030 [JSOI2007]文本生成器 补全AC自动机+简单DP
2017-12-11 14:19
489 查看
大家都吼强,可与之共勉 。
题意:您现在有n个单词,您得构造一只长度为m的文章,使得这个文章里面包含至少一个单词。(所有文本只包含大写字母)问构造方案数,答案对10007取模。
数据范围n≤60,m≤100。
题解:补集转化,AC自动机上面DP。
首先我们构造出这n个单词的AC自动机,然后考虑到求出能构造出的,我们可以用总方案数减去不能构造出的方案数。
不能构造出的就是在自动机走不到单词的尾节点,于是简单DP求出方案数。
复杂度O(m⋅节点数⋅26)。
补全AC自动机方便死了呢
/************************************************************** Problem: 1030 User: Lazer2001 Language: C++ Result: Accepted Time:192 ms Memory:82372 kb ****************************************************************/ # include <bits/stdc++.h> # define N 100010 int n, m ; short dp [6005] [6005] ; class AhoCrasickAutoMaton { private : int ncnt ; bool ban ; int go [26], fail ; public : inline void insert ( char* s ) { int cur = 0 ; for ( char *pt = s ; *pt ; ++ pt ) { if ( ! go [cur] [*pt - 'A'] ) go [cur] [*pt - 'A'] = ++ ncnt ; cur = go [cur] [*pt - 'A'] ; } ban [cur] = 1 ; } void build ( ) { fail [0] = -1 ; static std :: queue < int > Q ; for ( int i = 0 ; i < 26 ; ++ i ) if ( go [0] [i] ) Q.push ( go [0] [i] ) ; while ( ! Q.empty ( ) ) { int cur = Q.front ( ) ; Q.pop ( ) ; for ( int i = 0 ; i < 26 ; ++ i ) if ( go [cur] [i] ) { Q.push ( go [cur] [i] ) ; fail [go [cur] [i]] = go [fail [cur]] [i] ; } else { go [cur] [i] = go [fail [cur]] [i] ; } ban [cur] |= ban [fail [cur]] ; } } int Dp ( ) { dp [0] [0] = 1 ; for ( int i = 1 ; i <= m ; ++ i ) for ( int j = 0 ; j <= ncnt ; ++ j ) { if ( ban [j] ) continue ; for ( int k = 0 ; k < 26 ; ++ k ) { dp [i] [go [j] [k]] += dp [i - 1] [j] ; if ( dp [i] [go [j] [k]] >= 10007 ) dp [i] [go [j] [k]] -= 10007 ; } } int cnt1 = 0, cnt2 = 1 ; for ( int i = 0 ; i <= ncnt ; ++ i ) if ( ! ban [i] ) { cnt1 += dp [m] [i] ; if ( cnt1 >= 10007 ) cnt1 -= 10007 ; } for ( int i = 1 ; i <= m ; ++ i ) ( cnt2 *= 26 ) %= 10007 ; return ( cnt2 - cnt1 + 10007 ) % 10007 ; } } T ; int main ( ) { scanf ( "%d%d", & n, & m ) ; while ( n -- ) { static char s [6005] ; scanf ( "%s", s ) ; T.insert ( s ) ; } T.build ( ) ; printf ( "%d\n", T.Dp ( ) ) ; return 0 ; }
相关文章推荐
- bzoj 1030: [JSOI2007]文本生成器 (ac自动机上的dp)
- [BZOJ 1030][JSOI2007]文本生成器(AC自动机+DP)
- BZOJ1030 [JSOI2007]文本生成器(AC自动机+dp)
- BZOJ_1030_[JSOI2007]_文本生成器_(AC自动机+DP)
- [BZOJ1030][JSOI2007]文本生成器(AC自动机+dp)
- 【bzoj 1030】 [JSOI2007]文本生成器(AC自动机+dp)
- [BZOJ1030][JSOI2007]文本生成器(AC自动机+dp)
- bzoj 1030: [JSOI2007]文本生成器(AC自动机+DP)
- bzoj1030: [JSOI2007]文本生成器(AC自动机+Dp)
- bzoj 1030 [JSOI2007]文本生成器(AC自动机+DP)
- [BZOJ]1030: [JSOI2007]文本生成器 AC自动机+DP
- bzoj1030 [JSOI2007]文本生成器(AC+dp)
- bzoj 1030: [JSOI2007]文本生成器 (ac自己主动机上的dp)
- [bzoj1030][JSOI2007]文本生成器——AC自动机
- [BZOJ1030]-[JSOI2007]文本生成器-AC自动机+dp
- 【BZOJ1030】[JSOI2007]文本生成器【AC自动机】【计数DP】
- [BZOJ1030] [JSOI2007]文本生成器(AC自动机 + DP)
- BZOJ 1030: [JSOI2007]文本生成器 [AC自动机 DP]
- bzoj1030 [JSOI2007] 文本生成器(ACAM+dp)
- [Bzoj1030][JSOI2007]文本生成器(AC自动机)(dp)