题目大意:
  给定一个$1\sim n(n\leq10^5)$的全排列,有$m(m\leq10^5)$次操作,每次把区间$[l,r]$按照升序或降序排序。最后询问所有操作完成后,位置为$q$的数是多少。

思路:
  题目只需要求位置为$q$的数是多少,而并不关心其他的数是多少。因此排序时也只需要考虑答案的那个数。二分答案$k$,将$<k$的数当成0,$\geq k$的数当成1,原序列就变成了一个01序列。这样排序时只需要统计区间内0和1的个数,线段树区间修改即可。若排序后$q$上的值为1,则答案$\geq k$,否则$<k$。

 #include<cstdio>
#include<cctype>
#include<algorithm>
inline int getint() {
register char ch;
while(!isdigit(ch=getchar()));
register int x=ch^'';
while(isdigit(ch=getchar())) x=(((x<<)+x)<<)+(ch^'');
return x;
}
const int N=,M=;
int n,m,q,a[N];
struct Modify {
bool type;
int l,r;
};
Modify o[M];
class SegmentTree {
#define _left <<1
#define _right <<1|1
private:
int val[N<<],tag[N<<];
void push_up(const int &p) {
val[p]=val[p _left]+val[p _right];
}
void push_down(const int &p,const int &b,const int &e) {
if(tag[p]==-) return;
const int mid=(b+e)>>;
tag[p _left]=tag[p _right]=tag[p];
val[p _left]=tag[p]*length(b,mid);
val[p _right]=tag[p]*length(mid+,e);
tag[p]=-;
}
int length(const int &b,const int &e) const {
return e-b+;
}
public:
void build(const int &p,const int &b,const int &e,const int &k) {
if(b==e) {
val[p]=a[b]>=k;
return;
}
tag[p]=-;
const int mid=(b+e)>>;
build(p _left,b,mid,k);
build(p _right,mid+,e,k);
push_up(p);
}
void modify(const int &p,const int &b,const int &e,const int &l,const int &r,const bool &x) {
if(b==l&&e==r) {
tag[p]=x;
val[p]=x*length(b,e);
return;
}
push_down(p,b,e);
const int mid=(b+e)>>;
if(l<=mid) modify(p _left,b,mid,l,std::min(mid,r),x);
if(r>mid) modify(p _right,mid+,e,std::max(mid+,l),r,x);
push_up(p);
}
int query(const int &p,const int &b,const int &e,const int &l,const int &r) {
if(b==l&&e==r) return val[p];
push_down(p,b,e);
const int mid=(b+e)>>;
int ret=;
if(l<=mid) ret+=query(p _left,b,mid,l,std::min(mid,r));
if(r>mid) ret+=query(p _right,mid+,e,std::max(mid+,l),r);
return ret;
}
#undef _left
#undef _right
};
SegmentTree t;
inline bool check(const int &k) {
t.build(,,n,k);
for(register int i=;i<m;i++) {
const int opt=o[i].type,l=o[i].l,r=o[i].r,cnt1=t.query(,,n,l,r),cnt0=r-l+-cnt1;
if(opt==) {
if(cnt0) t.modify(,,n,l,l+cnt0-,);
t.modify(,,n,l+cnt0,r,);
}
if(opt==) {
if(cnt1) t.modify(,,n,l,l+cnt1-,);
t.modify(,,n,l+cnt1,r,);
}
}
return t.query(,,n,q,q);
}
int main() {
n=getint(),m=getint();
for(register int i=;i<=n;i++) a[i]=getint();
for(register int i=;i<m;i++) {
const int opt=getint(),l=getint(),r=getint();
o[i]=(Modify){opt,l,r};
}
q=getint();
int l=,r=n;
while(l<=r) {
const int mid=(l+r)>>;
if(check(mid)) {
l=mid+;
} else {
r=mid-;
}
}
printf("%d\n",l-);
return ;
}

[TJOI2016][HEOI2016]排序的更多相关文章

  1. BZOJ 4552: [Tjoi2016&Heoi2016]排序

    4552: [Tjoi2016&Heoi2016]排序 Time Limit: 60 Sec  Memory Limit: 256 MBSubmit: 579  Solved: 322[Sub ...

  2. bzoj千题计划128:bzoj4552: [Tjoi2016&Heoi2016]排序

    http://www.lydsy.com/JudgeOnline/problem.php?id=4552 二分答案 把>=mid 的数看做1,<mid 的数看做0 这样升序.降序排列相当于 ...

  3. [Tjoi2016&Heoi2016]排序[01序列]

    4552: [Tjoi2016&Heoi2016]排序 Time Limit: 60 Sec  Memory Limit: 256 MBSubmit: 994  Solved: 546[Sub ...

  4. 4552: [Tjoi2016&Heoi2016]排序

    4552: [Tjoi2016&Heoi2016]排序 链接 分析: 因为只询问一次,所以考虑二分这个数.显然是没有单调性的,但是我们可以二分所有大于等于mid的数中,是否有满足条件的x(而不 ...

  5. 【BZOJ4552】[Tjoi2016&Heoi2016]排序 二分+线段树

    [BZOJ4552][Tjoi2016&Heoi2016]排序 Description 在2016年,佳媛姐姐喜欢上了数字序列.因而他经常研究关于序列的一些奇奇怪怪的问题,现在他在研究一个难题 ...

  6. [bzoj4552][Tjoi2016][Heoi2016]排序

    Description 给出一个$1$到$n$的全排列,现在对这个全排列序列进行$m$次局部排序,排序分为$2$种: $1.(0,l,r)$表示将区间$[l,r]$的数字升序排序; $2.(1,l,r ...

  7. BZOJ4552: [Tjoi2016&Heoi2016]排序

    Description 在2016年,佳媛姐姐喜欢上了数字序列.因而他经常研究关于序列的一些奇奇怪怪的问题,现在他在研究一个难题 ,需要你来帮助他.这个难题是这样子的:给出一个1到n的全排列,现在对这 ...

  8. [bzoj4552][Tjoi2016&Heoi2016]排序-二分+线段树

    Brief Description DZY有一个数列a[1..n],它是1∼n这n个正整数的一个排列. 现在他想支持两种操作: 0, l, r: 将a[l..r]原地升序排序. 1, l, r: 将a ...

  9. bzoj 4552 [Tjoi2016&Heoi2016]排序 (二分答案 线段树)

    题目链接:https://www.lydsy.com/JudgeOnline/problem.php?id=4552 题意: 给你一个1-n的全排列,m次操作,操作由两种:1.将[l,r]升序排序,2 ...

  10. BZOJ 4552 [Tjoi2016&Heoi2016]排序 | 二分答案 线段树

    题目链接 题面 题目描述 在2016年,佳媛姐姐喜欢上了数字序列.因而他经常研究关于序列的一些奇奇怪怪的问题,现在他在研究一个难题,需要你来帮助他.这个难题是这样子的:给出一个1到n的全排列,现在对这 ...

随机推荐

  1. Redis实现之对象(三)

    集合对象 集合对象的编码可以是intset或者hashtable,intset编码的集合对象使用整数集合作为底层实现,集合对象包含的所有元素都被保存在整数集合里面.举个栗子,以下代码将创建一个图1-1 ...

  2. 基础_String

    String str1="hello"; String str2="hello"; String str3="hello"; String ...

  3. loj2065 「SDOI2016」模式字符串

    ref不是太懂 #include <iostream> #include <cstring> #include <cstdio> using namespace s ...

  4. asp.net中使用ffmpeg

    protected void Button1_Click(object sender, EventArgs e) { string FFmpegArguments = @" -i D:\离歌 ...

  5. 虚拟架构就绪 | 谈谈Windows Server 2012 R2迁移这件小事

    我们所说的“新选择”包括操作系统升级——告别Windows Server 2003或2008,选择用什么样的姿势进行升级呢? 新年伊始,正是企业对自身IT基础设施进行评估的最佳时期.在多项评估项目里面 ...

  6. C#入门篇6-2:字符串操作 string常用的函数

    //String 字符串的常见操作 public static void Fun1() { string MyStr = " Hello World! "; //length长度属 ...

  7. cegui 编译过程详解(cegui-0.8.2)

    cegui配置整了好长时间了,在一位大牛帮助下终于搞定了,网上的教程大多是老版本的,cegui-0.8.2版的配置寥寥无几,现在总结一下,献给正在纠结的小白们. 准备工作 第一步,先下载cegui-0 ...

  8. python - 接口自动化测试 - HttpRequest - 接口测试类封装

    # -*- coding:utf-8 -*- ''' @project: ApiAutoTest @author: Jimmy @file: http_request.py @ide: PyCharm ...

  9. c++ 吕凤翥 第六章 类和对象(二)

    c++ 吕凤翥 第六章 类和对象(二) 指针   引用  和数组 一:对象指针和对象引用 1.指向类的成员的指针 分为指向成员变量和指向成员函数两种指针 成员变量的格式:     类型说明符  类名: ...

  10. Java开发微信公众号(五)---微信开发中如何获取access_token以及缓存access_token

    获取access_token是微信api最重要的一个部分,因为调用其他api很多都需要用到access_token.比如自定义菜单接口.客服接口.获取用户信息接口.用户分组接口.群发接口等在请求的时候 ...