题意:给你n个数a1...an,接下来m次操作,每次操作(op,x),if(op==1)前x个数按照递增排列,if(op==2)前x个数按照递减排列,输出此n个数最终的顺序,(1 ≤ n, m ≤ 200 000,|ai|<=10^9)
分析:先不管op,根据x的大小,如果x比之前操作的x'都大,那么之前的操作就是无效的。但是,x之后的操作,x'比x小的数可以影响结果。所以,我们的思路是,先找到一个最大的x,在此x后的m'次操作中再次找到最大的x',把这些x值存下来,假设存到vector<node>v,struct node( op,id,val)中。把n个数ai压入multiset,从后到前扫描v,根据op的情况取出mutiset的前y个数还是后y个数。y值就是x-x'。
#include<iostream>
#include<string>
#include<stdio.h>
#include<string.h>
#include<vector>
#include<math.h>
#include<queue>
#include<map>
#include<set>
#include<algorithm>
using namespace std;
#define MAXN 200005
#define LL __int64
#define INF 0x3f7f7f7f
const double eps = 1e-10;
struct node
{
int op,id,val;
node(int op=0,int id=0,int val=0):op(op),id(id),val(val){}
}a[MAXN];
bool cmp(node x,node y)
{
if(x.val==y.val)
{
return x.id>y.id;
}
return x.val>y.val;
}
vector<node>v;
vector<int>ans;
multiset<int>mul;
multiset<int>::iterator it;
int num[MAXN];
int main()
{
int n,m,i,j;
while(scanf("%d%d",&n,&m)!=EOF)
{
mul.clear();
v.clear();
ans.clear();
for(i=1;i<=n;i++)
{
scanf("%d",&num[i]);
}
for(i=1;i<=m;i++)
{
scanf("%d%d",&a[i].op,&a[i].val);
a[i].id=i;
}
sort(a+1,a+1+m,cmp);//按照val值从大到小排序
int nowid=a[1].id;//记录当前id
v.push_back(node(a[1].op,a[1].id,a[1].val));
for(i=2;i<=m;i++)
{
if(a[i].id>nowid)//必须是比当前id大的才压入
{
nowid=a[i].id;
v.push_back(node(a[i].op,a[i].id,a[i].val));
}
}
for(i=n;i>a[1].val;i--)
{
ans.push_back(num[i]);//没参与排序的数就直接保存下来
}
for(i=1;i<=a[1].val;i++)
{
mul.insert(num[i]);//参与排序的数压入multiset
}
int sz=v.size();
for(i=0;i<sz;i++)
{
int op=v[i].op;
int val=v[i].val;
int id=v[i].id;
if(op==1)
{
if(i!=sz-1)
{
int nextval=v[i+1].val;//和下一次的val比较,可以知道哪些数是固定了的
for(j=1;j<=val-nextval;j++)
{
it=mul.end();
it--;
ans.push_back(*it);
mul.erase(it);
}
}
else
{
while(!mul.empty())
{
it=mul.end();
it--;
ans.push_back(*it);
mul.erase(it);
}
}
}
else
{
if(i!=sz-1)
{
int nextval=v[i+1].val;
for(j=1;j<=val-nextval;j++)
{
it=mul.begin();
ans.push_back(*it);
mul.erase(it);
}
}
else
{
while(!mul.empty())
{
it=mul.begin();
ans.push_back(*it);
mul.erase(it);
}
}
}
}
sz=ans.size();
for(i=sz-1;i>=0;i--)
{
printf("%d",ans[i]);
if(i!=0)printf(" ");
else printf("\n");
}
}
return 0;
}