HDU-5532 Almost Sorted Array (LIS)

题目大意:给一个n个数的序列,问这个序列删掉一个数后是否有序。

题目分析:找最长上升子序列和最长下降子序列,只要有一个的长度不小于n-1即可。

代码如下:

# include<iostream>
# include<cstdio>
# include<cmath>
# include<vector>
# include<list>
# include<queue>
# include<map>
# include<set>
# include<cstring>
# include<algorithm>
using namespace std;

const int N=100005;

int n;
int a[N+5];
int dp[N+5];
int d[N+5];

int f(int l,int r,int x)
{
	while(l<r)
	{
		int mid=l+(r-l)/2;
		if(d[mid]<=x)
			l=mid+1;
		else
			r=mid;
	}
	return l;
}

int f1(int l,int r,int x)
{
	while(l<r)
	{
		int mid=l+(r-l)/2;
		if(d[mid]>=x)
			l=mid+1;
		else
			r=mid;
	}
	return l;
}

int main()
{
	int T;
	scanf("%d",&T);
	while(T--)
	{
		scanf("%d",&n);
		for(int i=0;i<n;++i) scanf("%d",a+i);
		d[0]=a[0];
		int cnt=0;
		int len=1;
		for(int i=1;i<n;++i){
			if(a[i]>=d[len-1])
				d[len++]=a[i];
			else{
				int pos=f(0,len,a[i]);
				d[pos]=a[i];
			}
		}
		if(len>=n-1)
			++cnt;
		d[0]=a[0];
		len=1;
		for(int i=1;i<n;++i){
			if(a[i]<=d[len-1]){
				d[len++]=a[i];
			}else{
				int pos=f1(0,len,a[i]);
				d[pos]=a[i];
			}
		}
		if(len>=n-1)
			++cnt;
		if(cnt==0)
			printf("NO
");
		else
			printf("YES
");
	}
	return 0;
}

  

原文地址:https://www.cnblogs.com/20143605--pcx/p/5471817.html