传送门:http://www.lydsy.com/JudgeOnline/problem.php?id=2298
如果一个人说a个人比他大,b个人比他小,也就是他声称[b+1,,n-a]的值是相等的(好像可以并查集)
问题转化为给一些线段,找出一些线段,价值最大
说起来简单,其实还有各种蛋疼
如果a+b>=n那么直接无视
如果有多个相同的区间,那么价值是min(r-l+1,出现次数)
二分优化dp
Code:
#include<bits/stdc++.h>
using namespace std;
const int maxn=1e5+5;
int f[maxn];
int n;
struct pii{
int x,y,c;
bool f;
};
pii a[maxn];
bool cmp(pii a,pii b){return a.y<b.y||(a.y==b.y&&a.x<b.x);}
map<pair<int,int>,int>M;
int main(){
scanf("%d",&n);
for(int i=1;i<=n;i++){
scanf("%d%d",&a[i].x,&a[i].y);
a[i].f=a[i].x+a[i].y>=n;
a[i].x=n-a[i].x;
a[i].y++;
if(a[i].x>a[i].y)swap(a[i].x,a[i].y);
a[i].c=min(M[make_pair(a[i].x,a[i].y)]+=a[i].f^1,a[i].y-a[i].x+1);
}sort(a+1,a+1+n,cmp);
for(int i=1;i<=n;i++){
if(a[i].f){f[i]=f[i-1];continue;}
int l=lower_bound(a+1,a+i,(pii){-1,a[i].x},cmp)-a-1;
f[i]=max(f[i-1],f[l]+a[i].c);
}cout<<n-f[n]<<endl;
return 0;
}