您的位置:首页 > 其它

【最长非上升子序列】删除最少的元素

2018-03-09 10:51 351 查看


其实就是最长上升子序列的一种变相,要求最长非上升子序列,其实就是把大小顺序换一下,替换是去替换子序列中那个第一个比你小的数。分两次,从头和从尾开始,dp[i]表示到达i的子序列长度。加起来-1就是两个序列到i的长度和。#include<iostream>
#include<bits/stdc++.h>
using namespace std;

int main()
{
int n;
cin>>n;
long long a[n+1];
for(int i=1;i<=n;i++)
cin>>a[i];
int dp[n+1];
int len1=1,len2=1;
long long ans1[n+1],ans2[n+1];
memset(dp,0,sizeof(dp));
memset(ans1,0,sizeof(ans1));
memset(ans2,0,sizeof(ans2));
ans1[1]=a[1];
ans2[1]=a
;
dp[1]=1; //注意
for(int i=2;i<=n;i++)
{
if(a[i]<ans1[len1])
{
ans1[++len1]=a[i];
}
else
{
int pos=len1;
while(ans1[pos]<a[i] && pos!=0)
pos--;
ans1[pos+1]=a[i];
}
dp[i]=len1;
}

dp
+=1; //注意
for(int i=n-1;i>=1;i--) //注意
{
if(a[i]<ans2[len2])
{
ans2[++len2]=a[i];
}
else
{
int pos=len2;
while(ans2[pos]<a[i] && pos!=0)
pos--;
ans2[pos+1]=a[i];
}
dp[i]+=len2;
}
int maxx=0;
for(int i=1;i<=n;i++)
{ if(maxx<dp[i])
maxx=dp[i];
}
cout<<n-(maxx-1);
return 0;
}对于代码中标注的细节要注意。我这里是直接用一个dp来存长度,也可以分别用dp1 dp2数组最后相加找最大值。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: