LUOGU P3147 [USACO16OPEN]262144
解题思路
比较巧妙的dp,f[i][j]表示到了第j位,合成了i,此时的右端点 。初值f[a[i]][i]=i+1,转移方程f[i][j]=f[i-1][f[i-1][j]]
代码
#include<iostream>
#include<cstdio>
using namespace std;
const int MAXN = 262150;
inline int rd(){
int x=0,f=1;char ch=getchar();
while(!isdigit(ch)) {f=ch=='-'?-1:1;ch=getchar();}
while(isdigit(ch)) {x=(x<<1)+(x<<3)+ch-'0';ch=getchar();}
return x*f;
}
int n,f[85][MAXN],ans; //f[i][j]表示到了第j位,合成了i,此时的右端点
int main(){
n=rd();
for(register int i=1;i<=n;i++) f[rd()][i]=i+1;
for(register int i=1;i<=60;i++)
for(register int j=1;j<=n;j++){
if(!f[i][j]) f[i][j]=f[i-1][f[i-1][j]];
if(f[i][j]) ans=i;
}cout<<ans<<endl;
return 0;
}