bzoj1030 JSOI2007 文字生成器

2021-07-09 07:23:47 字數 1558 閱讀 5551

time limit: 1 sec  

memory limit: 162 mb

submit: 2891  

solved: 1193 [

submit][

status][

discuss]

jsoi交給隊員zyx乙個任務,編制乙個稱之為「文字生成器」的電腦軟體:該軟體的使用者是一些低幼人群,他們現在使用的是gw文字生成器v6版。該軟體可以隨機生成一些文章―――總是生成一篇長度固定且完全隨機的文章—— 也就是說,生成的文章中每個位元組都是完全隨機的。如果一篇文章中至少包含使用者們了解的乙個單詞,那麼我們說這篇文章是可讀的(我們稱文章a包含單詞b,當且僅當單詞b是文章a的子串)。但是,即使按照這樣的標準,使用者現在使用的gw文字生成器v6版所生成的文章也是幾乎完全不可讀的。 zyx需要指出gw文字生成器 v6生成的所有文字中可讀文字的數量,以便能夠成功獲得v7更新版。你能幫助他嗎? 

輸入檔案的第一行包含兩個正整數,分別是使用者了解的單詞總數n (<= 60),gw文字生成器 v6生成的文字固定長度m;以下n行,每一行包含乙個使用者了解的單詞。 這裡所有單詞及文字的長度不會超過100,並且只可能包含英文大寫字母a..z  。 

乙個整數,表示可能的文章總數。只需要知道結果模10007的值。 

2 2ab

100畢竟是自己做的第一道ac自動機題,還是小小地慶祝一下吧……

我們假設在trie樹中表示單詞結尾的節點為結尾點。

在新增失配邊後,trie樹就轉化成乙個有向圖,問題也就轉化成:從起點出發,走m步,至少路過乙個結尾點的方案數。

這就可以用動態規劃來實現了。具體方法如下:

用f[i][j][0]表示走i步到達j點不經過結尾點的方案數,用f[i][j][1]表示走i步到達j點經過結尾點的方案數。

我們很容易可以想到狀態轉移方程。(詳見程式)

最終答案為∑(i)f[m][i][1],注意每次計算後都要取模。

#include#include#include#include#include#include#include#define f(i,j,n) for(int i=j;i<=n;i++)

#define d(i,j,n) for(int i=j;i>=n;i--)

#define ll long long

#define pa pair#define mod 10007

using namespace std;

int t[6010][26],f[110][6010][2],v[6010],go[6010];

int n,m,tot;

char s[110];

queueq;

inline int read()

while (ch>='0'&&ch<='9')

return x*f;

}inline void insert()

v[now]=1;

}inline void bfs()

else t[x][i]=j?t[j][i]:1;

} }}inline void dp()

}int main()

BZOJ1030 JSOI2007文字生成器

比起前面hnoi的gt考試,貌似這題是多模式串。然後我滾去學ac自動機了。發現還是很好寫的。ac自動機部分見筆記 搞出自動機之後,f i j 表示自動機上第i個節點匹配到第j個字元不可讀文字的數量,然後自己yy一下轉移 include include include define n 10005 d...

bzoj1030 JSOI2007 文字生成器

傳送門 思路 直接算好像比較困難,所以考慮先算不可讀的串的個數,再拿總串數去減。不可讀的串的數量就是在ac自動機上走m步而不經過結尾節點 包括結尾點和fail指向結尾點的節點 的路徑條數。這個怎麼求呢?設f i j 表示走i步,現在在j號節點的路徑條數。那麼f i j 可以轉移f i 1 son j...

bzoj1030 JSOI2007 文字生成器

jsoi交給隊員zyx乙個任務,編制乙個稱之為 文字生成器 的電腦軟體 該軟體的使用者是一些低幼人群,他們現在使用的是gw文字生成器v6版。該軟體可以隨機生成一些文章 總是生成一篇長度固定且完全隨機的文章 也就是說,生成的文章中每個位元組都是完全隨機的。如果一篇文章中至少包含使用者們了解的乙個單詞,...