最长严格上子序列(二分优化)

http://codevs.cn/problem/3955/  原题网站
题目描述 Description

给一个数组a1, a2 ... an,找到最长的上升降子序列ab1<ab2< .. <abk,其中b1<b2<..bk。

输出长度即可。

输入描述 Input Description

第一行,一个整数N。

第二行 ,N个整数(N < = 1000000)

输出描述 Output Description

输出K的极大值,即最长不下降子序列的长度

样例输入 Sample Input

5

9 3 6 2 7

样例输出 Sample Output

3

数据范围及提示 Data Size & Hint

n<=1000000

为了方便大家调试,数据名称已被修改——THREE

#include<iostream>
#include<cstdio>
using namespace std;
int a[1000001],f[1000001];//用于记录数列中单调不下降的值,是有序的。
int find(int *a,int len,int n)//二分查找当前元素应在f中的下标
{
int l=0,r=len,mid=(l+r)/2;
while (l<=r)
{
if (a[mid]>n) r=mid-1;
else if (a[mid]<n) l=mid+1;
else return mid;
mid=(l+r)/2;
}
return l;
}
int main()
{
int n,len,j;//len用于记录f中以求出元素的最大下标
cin>>n;
for (int i=0;i<=n-1;i++)
cin>>a[i];

f[1]=a[0];

len=1;//此时数组f中只有一个元素,最大下标为1
for (int i=1;i<=n;i++)
{
j=find(f,len,a[i]);
f[j]=a[i];
if (j>len)//更新len(由于二分查找,j只能比len大1)
len=j;
}
cout<<len;
return 0;
}

I'm so lost but not afraid ,I've been broken and raise again
原文地址:https://www.cnblogs.com/sjymj/p/5180446.html