1.喵星球的點名
發現這種多串匹配不用廣義字尾自動機而用 字尾陣列就是chishi。
所以當然是大力廣義字尾自動機了。
我們找到每個模式串的節點,並將之所有父鏈節點的大小全部加一來方便查詢。
匹配的時候直接輸出匹配的末尾節點的大小,並且將之的標記+1。
最後再次掃一次父鏈節點,把標記全部統計出來即可。
複雜度是:\(o(n^)\),由於暴跳父親。
但是這樣的上界遠遠達不到。
甚至比字尾陣列的大常數log跑的還快的多得多。
2.字串
仍然字尾自動機暴力水過。
先翻轉串。
首先對於每個節點線段樹合併求出\(endpos\)集合。
考慮二分答案。
然後從字首節點跳father跳到合適的\(len\)處。
這個過程可以直接用倍增來實現。
然後直接判斷這個節點的\(endpos\)集合中是否含有\([a,b]\)之間的元素就可以了。
3.yww 與字串
這個題意思就是帶限制的本質不同子串數目。
我們對於每個節點都維護乙個\(w\)值代表他所能向左延伸的最長長度。
那麼每個節點對本質不同子串的貢獻就是:$$max(min(len[x],w[x])-len[fa[x]],0)$$
\(mx\)維護的時候要取\(max\),因為一定是取長度最長的那乙個,也是由於所有本質相同的子串只要有乙個是"好"的,那麼就可以計算貢獻。
4.外星聯絡
水的很,直接建字尾樹然後暴力dfs一次輸出即可。
5.跳蚤
挺難的題。
而且只能用字尾陣列來做。
首先二分答案在所有本質不同子串的排名。
考慮如何check。
我們從字串的末尾開始乙個乙個的向前加入字元,如果當前的字串排名已經大於當前二分串的排名,那麼此時必須切一刀。
最後只需要判斷切的次數和\(k\)的關係就可以調整二分上下界了。
考慮為什麼是對的。
假設我們是從前往後加入字元的話,需要判斷的是\([l,i],[l+1,i]……,[i,i]\)這些字串中最大的乙個是否排名大於二分的答案。
不是很好判斷。
而我們如果從後向前加入字元的話,需要判斷的是\([i,r],[i,r-1],……,[i,i]\)這些字串中字典序最大的顯然是\([i,r]\),只需要處理這乙個串的大小即可。
假設已經的到了排名。
首先考慮如何由排名得到答案。
我們對於每個字尾按位置處理出這樣乙個陣列:\(ra[i]\),含義是\(suffix(i)\)在所有本質不同子串中的排名。
這樣的話得到轉移方程:
\[ra[sa[i]]=ra[sa[i-1]]+(n-sa[i]+1)-height[i]
\]也就是說除了\(lcp\)的部分,每乙個位置都會產生乙個本質不同子串。
這樣我們完全可以線性的按照\(rk\)列舉字尾來求出\(ra\)陣列。
求出後再次線性列舉,得到第乙個使得\(ra[sa[i]]>=k\)的排名為\(i\)的字尾。
那麼就很簡單了,串的起點就是\(sa[i]\)了,那末尾就是\(n+k-ra[sa[i]]\)也就是串\(s[sa[i],n+k-ra[sa[i]]]\)
那麼考慮對於給定的\(s[l,r]\)如何求出其排名。
首先找到這個串第一次(按rk來說的第一次)出現的字尾是哪個。
這個很簡單,直接二分\([1,rk[l]]\)的所有字尾即可,因為要得\(rk\)到盡量靠前並且\(lcp(sa[mid],l)>=len\)的字尾,所以具有單調性。
如果找到了這個位置就好說了,設這個字尾為\(suffix(sa[x])\)。
這個子串的本質不同排名就是\(ra[sa[x]]-(n-sa[x]+1-len)\)
這個就是\(wzz\)學長說的唯一的字尾陣列可以辦但是字尾自動機做不了的了。
對於模式串的任意排名,\(logn\)的求出串的位置。
對於任意的模式串子串,\(logn\)的求出串的排名。
6.**的**
仍然用字尾陣列來做。
其實差分之後就是在找\(aba\)形式的本質不同子串。
考慮列舉\(a\)的長度。
這樣暴力來做的話複雜度是\(n^2lnn\)的。
但是我們考慮另外一種方法。
將模式串每\(a\)個分一塊。
然後對於每塊的起點\(i\)求出他和另乙個位置\(i+a+m\)的最長前字尾長度,然後由於可以平移。
那麼設\(lcp+lcs=w\),那麼這一塊作出的貢獻就是:\(w-a\)
這樣複雜度是:
\[\sum\limits_^\frac=nln n
\]
字尾陣列2
o n 2 隨便水 考慮二分答案,二分答案串在原串中的排名。考慮如何 check 從後向前掃每個串,每次在串的前面加入乙個字元,如果這個串的字典序 當前串,那麼在這個地方斷掉。最後檢驗次數是否小於 k 即可。對於比較兩個串字典序的問題,直接用字尾陣列求 lcp 就可以做到 o 1 比較。似乎是個套路...
字尾陣列總結
附模板 字尾陣列 void build sa int m,int n int x wa,y wb,t for int i 0 i 0 i sa c x i i for int k 1 k n k 1 int p 0 for int i n k i k y p sa i k for int i 0 i...
字尾陣列總結
2子串個數問題 3迴圈子串問題 兩個字串串問題 2子串個數問題 多個字串問題總結 首先,使用倍增演算法求出對應sa,height值,時間複雜度o nlog n 具體定義參考國家集訓隊2009羅穗騫 中還給出一種線性dc3做法 include using namespace std const int...