其他分享
首页 > 其他分享> > Luogu P3287 [SCOI2014]方伯伯的玉米田

Luogu P3287 [SCOI2014]方伯伯的玉米田

作者:互联网

题链

分析

发现:对于每次修改操作\([L,R]\),对\(L\)有正影响,对\(R+1\)有负影响
所以每次修改\([L,n]\)
设\(f[i][j]\)表示前\(i\)个修改\(j\)次的最长LIS

\[f[i][j]=max(f[k][l])+1,j>=l&&a[i]+j>=a[k]+l \]

用二维树状数组维护即可

#include<bits/stdc++.h>
using namespace std;

const int N=1e4+5;
int n,m,mx,c[6005][505],a[N];

inline void add(int x,int y,int t) {
	for(int i=x;i<=mx;i+=i&-i) {
		for(int j=y;j<=m+1;j+=j&-j) c[i][j]=max(c[i][j],t);
	}
}

inline int ask(int x,int y) {
	int ret=0;
	for(int i=x;i;i-=i&-i) {
		for(int j=y;j;j-=j&-j) ret=max(ret,c[i][j]);
	}
	return ret;
}
int main() {
	scanf("%d%d",&n,&m); mx=0;
	for(int i=1;i<=n;i++) {
		scanf("%d",&a[i]);
		mx=max(mx,a[i]+m);
	}
	for(int j=0;j<=m;j++) {
		add(a[1]+j,j+1,1);
	}
	int ans=1;
	for(int i=2;i<=n;i++) {
		for(int j=m;j>=0;j--) {
			int t=ask(a[i]+j,j+1)+1;
			ans=max(ans,t);
			add(a[i]+j,j+1,t);
		}
	}
	printf("%d\n",ans);
	return 0;
}

标签:max,int,Luogu,玉米田,每次,修改,add,ans,SCOI2014
来源: https://www.cnblogs.com/wsfwsf/p/14445098.html