题意:给出字符串 s 和 t,每次操作将 s 中出现的第一个 t 删去,直到不能删为止。求最后的串。
|s|<=1e6
题解:hash 做法。(此题也有 kmp 和权值线段树做法)
因为涉及到删除操作,所以我们要动态的实现这个过程。所以考虑开一个栈来存储当前留下的字符。
然后每有一个字符入栈,就拿当前栈顶的 hash 值来算现在的 hash 值。这样就保证了我的栈中每个位置的 hash 值是连续的。
那么就可以用正常字符串 hash 的方法来判断现在栈顶的 |t| 个字符是否和 t 一致了。如果相同,直接栈顶-=|t|,接下来再从新的栈顶开始做就行。
答案就是最后栈中剩下的东西
char s[1000010], t[1000010];
long long adjust = 1, stk[1000010], goal;
int lens, lent, top = 0, ans[1000010];
int main() {
scanf("%s%s", s+1, t+1);
lens = strlen(s+1), lent = strlen(t+1);
for(int i = 1; i <= lent; ++i) adjust = adjust * base % mod;
for(int i = 1; i <= lent; ++i) goal = (goal * base + t[i] - 'a' + 1) % mod;
for(int i = 1; i <= lens; ++i) {
stk[top + 1] = (stk[top] * base + s[i] - 'a' + 1) % mod; top++;
ans[top] = i;
if(top >= lent && ((stk[top] - stk[top - lent] * adjust % mod) % mod + mod) % mod == goal) top -= lent;
}
for(int i = 1; i <= top; ++i) putchar(s[ans[i]]);
return 0;
}
标签:1000010,洛谷,int,题解,top,lent,hash,P4824,mod
From: https://www.cnblogs.com/1358id/p/17373301.html