總結 字尾2

2022-03-26 02:50:19 字數 2274 閱讀 7203

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...