扩展KMP
题目意思:
题目的 hit 解释很清楚。
本题要点:
1、 做法: 先把 s1 和 s2 来个翻转。以 s1 为母串, s2 为子串, 运行 扩展 KMP 算法,
extend[i] 表示 s2的子串 s2[i, … , extend[i] + i - 1] 与 s1 的子串 s1[0, …, extend[i] - 1] 相等。
这样就说明了, 以下的子串都相等。
s2[i, ... , extend[i] + i - 2] == s1[0, ..., extend[i] - 2]
s2[i, ... , extend[i] + i - 3] == s1[0, ..., extend[i] - 3]
s2[i, ... , extend[i] + i - 4] == s1[0, ..., extend[i] - 4]
...
s2[i, ... , i + 2] == s1[0, ..., 2]
s2[i, ... , i + 1] == s1[0, ..., 1]
所以,当遇到 extend[i] != 0 时候,从 1 累加到 extend[i], 等差数列,和为 extend[i] * (extend[i] + 1) / 2
2、以上各式子,累加起来就是题目所求。
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;
const int MaxN = 1e6 + 10;
const long long mod = 1e9 + 7;
int Next[MaxN];
int extend[MaxN]; // extend[i] 表示 子串 T与 母串 S[i, n-1]的最长公共前缀
char s1[MaxN], s2[MaxN];
int T;
//预处理next 数组
void getNext(char* str)
{
int i = 0, j, po, len = strlen(str);
Next[0] = len;
wh