http://codeforces.com/problemset/problem/340/D
题意:给出一个n个数构成的排列,类似冒泡排序,若a[i]>a[i+1] a[i]-a[i+1]连边 并swap(a[i],a[i+1])
反复操作 直到排序结束,n<=1e5,问该图构成的最大独立集大小为?
最大独立集:集合中任意两点无边相连.
直接建图显然不行,找规律:a[i]和后面比它大的都不会连边.
a[i],x,y下标递增,冒泡排序,a[i]<x<y x和y不可能交换
x>y 则x一定会被交换到y之后 每次又是两个相邻元素交换 则x-y一定有边
所以 本题独立集的元素单调递增 O(nlogn)求LIS即可
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int inf=1e9; const int N=2e5+20; int n,a[N],f[N]; int L[N];//L[i],LIS3¤?è?aiμ?×?D??á?2a[j] int main() { while(cin>>n) { for(int i=1;i<=n;i++) scanf("%d",&a[i]),L[i]=inf; L[0]=-inf; for(int i=1;i<=n;i++) { int l=0,r=n; while(l<=r) { int mid=(l+r)>>1; if(a[i]>L[mid]) l=mid+1; else r=mid-1; } f[i]=l; L[l]=a[i];//L[l]>a[i] //a[i]>L[l-1] ?üD?L[l]oó L[l]>L[l-1] LDòáDòàè?μ¥μ÷μY?? } int ans=0; for(int i=1;i<=n;i++) ans=max(ans,f[i]); cout<<ans<<endl; } return 0; }
时间: 2024-11-05 16:44:34