[习题练习] 后缀数组
A
题意
求不可重叠的最长重复字符串
题解
建立\(SA\),那么最长的重复字符串一定满足
\(sa_i + LCP(i, j) \leq sa_j\)
用二分来枚举最长重复字符串的长度\(mid\),那么对应一个区间\([l,r]\)
只要满足\(\min(height_i) \geq mid\)并且存在\(sa_i + mid \leq sa_j\) 就满足条件。
Code
B
题意
可重叠最长重复子串次数大于k
题解
跟上题类似,二分一个子串长度\(mid\)
只要有一个连续\(height\)区间 满足区间\(height\)值\(\geq mid\)
且区间长度\(\geq k\) 及满足条件
Code
C/D
题意
求字符串中本质不同的子串的数量
题解
考虑容斥原理,字符串总的子串的数量是\(\frac{n(n+1)}{2}\)
而重复的数量,我们考虑任意子串都是某个后缀的前缀
所以答案就是\(\frac{n(n+1)}{2}-\sum_{i=1}^n height_i\)
Code
E
题意
求最长字符串循环节长度
题解
可以用\(KMP\)算法,\(\frac{n} {n - next_n}\) 必须是整除,否则答案为1
同样可以用\(SA\),但是如果不用\(\text{DC-3}\) 会超时。
那么我们找到\(height_{rk_1}\)的长度,那么答案就是\(\frac{n} {n - height_{rk_1}}\) 必须是整除,否则答案为1
画图比较好理解。
F
题意
求子串的最长字符串循环节长度
题解
缘 妙不可言