0%

Edu-CF-178-E. Unpleasant Strings

思路讲解

首先贪心的,我们在每个位置上总归想跳的最远,且在每个位置上都跳的最远,得到的一定是最少跳跃次数的。

那么这个每个位置上通过加一个字母能够一次跳到的最远位置怎么得到的那?其实就是所有合法字母中上一次出现的位置最远的字母的位置(如果有一个合法字母前面没出现过,那我们就认为他直接跳出去结束了)。

1
2
3
4
5
6
7
8
9
10
11
12
ROF(i,N-1,0){
FOR(j,0,K-1){
if(Pos[j].empty()){
JumpFar[i]=N;
JumpCh[i][j]=N;
}else{
JumpFar[i]=max(Pos[j].back(),JumpFar[i]);
JumpCh[i][j]=Pos[j].back();
}
}
Pos[S[i]-'a'].pb(i);
}

然后知道了在这个位置上最远能跳多远,那么我们知道最多要跳多少次那?可以通过记忆化搜索。

1
2
3
4
5
6
7
8
9
ll dfs(ll x){
if(x>=N) return 0;
if(dp[x]!=0) return dp[x];
return dfs(JumpFar[x])+1;
}

ROF(i,N-1,0){
dp[i]=dfs(i);
}

最后这个串需要用多少位原串需要跳跃处理,否则会 TLETLE,最坏 O(NQ)O(NQ) 时间复杂度。

AC代码

https://codeforces.com/contest/2104/submission/317799371

心路历程(WA,TLE,MLE……)

https://codeforces.com/contest/2104/submission/317796467

对比对部分没有优化。