这个题,我是先找到比第k个元素小的并且在它前面的,和比它大在它后面的元素,放到一个数组里,就保证我们找的最长上升子序列里一定包含第K个元素了,在新的数组里跑一遍最长上升子序列就行了,我发现我的做法跟DQS神犇的一样,然而本蒟蒻只会O(n²)的方法啊,QAQ,于是在T掉两个点后跑去学了O(nlog(n))的方法,就A了。。。。
#include <cstdio>
#include <iostream>
#include <cstring>
#include <algorithm>
#define INF 2147483640
using namespace std;
int a[800000];
int b[800000];
int dp[800000];
int main()
{
int n,m;
scanf("%d%d",&n,&m);
for(int i = 1; i <= n ; i ++)
{
scanf("%d",&a[i]);
}
int ans = 0,tot= 0;
for(int i = 1; i <= m ; i ++)
{
if(a[i] <= a[m])
b[++tot] = a[i];
}
for(int i = m; i <= n ; i ++)
{
if(a[i] > a[m])
b[++tot] = a[i];
}
for(int i = 1; i <= tot; i ++)
dp[i] = INF;
for(int i = 1; i <= tot; i ++)
{
dp[lower_bound(dp+1,dp+1+tot,b[i])-dp] = b[i];
}
printf("%d",lower_bound(dp+1,dp+1+tot,INF)-dp-1);
return 0;
}