p5156 [USACO18DEC]Sort It Out
Posted yzxverygood
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了p5156 [USACO18DEC]Sort It Out相关的知识,希望对你有一定的参考价值。
分析
我们发现对于没有发现的点相对位置不会发生改变
于是我们可以吧问题转化为求一个lis
于是我们字典序第k小的答案就是字典序第k大的lis
代码
#include<iostream>
#include<cstdio>
#include<cstring>
#include<string>
#include<algorithm>
#include<cctype>
#include<cmath>
#include<cstdlib>
#include<ctime>
#include<queue>
#include<vector>
#include<set>
#include<map>
#include<stack>
using namespace std;
#define int long long
const int inf = 1e18;
int a[100100],pl[100100],sum[100100],n,m;
vector<int>v[100100];
bool is[100100];
struct node {
int ans,tot;
};
node d[100100];
inline void add(node &x,node y){
if(x.ans<y.ans)x.ans=y.ans,x.tot=y.tot;
else if(x.ans==y.ans)x.tot=min(inf,x.tot+y.tot);
}
inline int lb(int x){return x&(-x);}
inline node q(int x){node res={0,1ll};while(x<=n)add(res,d[x]),x+=lb(x);return res;}
inline void add(int x,node k){while(x)add(d[x],k),x-=lb(x);}
signed main(){
int i,j,k;
scanf("%lld%lld",&n,&k);
for(i=1;i<=n;i++)scanf("%lld",&a[i]),pl[a[i]]=i;
for(i=n;i>0;i--){
node res=q(pl[i]+1);
res.ans++;
v[res.ans].push_back(i);
sum[i]=res.tot;
add(pl[i],res);
}
m=q(1).ans;
int P=-1;
for(i=m;i>0;i--)
for(j=0;j<v[i].size();j++){
if(pl[v[i][j]]<P)continue;
if(sum[v[i][j]]>=k){
is[v[i][j]]=1;
P=pl[v[i][j]];
break;
}else k-=sum[v[i][j]];
}
printf("%lld
",n-m);
for(i=1;i<=n;i++)
if(!is[i])printf("%lld
",i);
return 0;
}
以上是关于p5156 [USACO18DEC]Sort It Out的主要内容,如果未能解决你的问题,请参考以下文章