LIS模板
有N个整数,输出这N个整数的最长上升序列、最长下降序列、最长不上升序列和最长不下降序列。
根据上述分析,我们应该十分容易就能够写出最后的程序,四个序列的代码基本相似
转载此处:https://blog.csdn.net/Ronaldo7_ZYB/article/details/81111678(可看大佬更详细直接的lis算法)
代码如下:
#include<bits/stdc++.h>
using namespace std;
int n;
int a[800000];
int f[800000];
void Lis1()
{
memset(f,0,sizeof(f));
int len=0,pos;f[0]=-pow(10,9);
for (int i=1;i<=n;i++)
{
if (a[i]>f[len]) f[++len]=a[i];
else
{
int L=1,R=len,Mid;
while (L+1<R)
{
Mid=(L+R)>>1;
if (a[i]>f[Mid]) L=Mid;
else R=Mid;
}
if (a[i]>f[L]) pos=R;
else pos=L;
f[pos]=min(f[pos],a[i]);
}
}
cout<<len<<endl;
}
void Lis2()
{
memset(f,0,sizeof(f));
int len=0,pos;f[0]=pow(10,9);
for (int i=1;i<=n;i++)
{
if (a[i]<f[len]) f[++len]=a[i];
else
{
int L=1,R=len,Mid;
while (L+1<R)
{
Mid=(L+R)>>1;
if (a[i]<f[Mid]) L=Mid;
else R=Mid;
}
if (a[i]<f[L]) pos=R;
else pos=L;
f[pos]=max(f[pos],a[i]);
}
}
cout<<len<<endl;
}
void Lis3()
{
memset(f,0,sizeof(f));
int len=0,pos;f[0]=pow(10,9);
for (int i=1;i<=n;i++)
{
if (a[i]<=f[len]) f[++len]=a[i];
else
{
int L=1,R=len,Mid;
while (L+1<R)
{
Mid=(L+R)>>1;
if (a[i]<=f[Mid]) L=Mid;
else R=Mid;
}
if (a[i]<=f[L]) pos=R;
else pos=L;
f[pos]=max(f[pos],a[i]);
}
}
cout<<len<<endl;
}
void Lis4()
{
memset(f,0,sizeof(f));
int len=0,pos;f[0]=-pow(10,9);
for (int i=1;i<=n;i++)
{
if (a[i]>=f[len]) f[++len]=a[i];
else
{
int L=1,R=len,Mid;
while (L+1<R)
{
Mid=(L+R)>>1;
if (a[i]>=f[Mid]) L=Mid;
else R=Mid;
}
if (a[i]>=f[L]) pos=R;
else pos=L;
f[pos]=min(f[pos],a[i]);
}
}
cout<<len<<endl;
}
int main()
{
ios::sync_with_stdio(false);
cin>>n;
for (int i=1;i<=n;i++)
cin>>a[i];
Lis1();
Lis2();
Lis3();
Lis4();
return 0;
}