【NOIP2016模拟7.11】排序
来源:互联网 发布:苏州程序员招聘 编辑:程序博客网 时间:2024/05/02 12:27
Description
The solution
不错的题目,不错到感动至极。。。
懒癌发作,不想想太多了。。
脑力劳动,疲惫至极,
神志不清,食欲不振
好像身体被掏空。。。
咦?扯远了。。。(⊙﹏⊙)b。。。o(╯□╰)o。。。
题解献上
对于100%的数据,可以通过二分答案,每次二分的值为a,将整个序列
中大于等于a的值变为1,小于a的值变成0。这样序列中只有0和1,对于每
一次部分排序,我们可以通过线段树的区间更新,若为升序排序,则把该
区间的0全部排在区间前段,1排在区间后段,最后全部部分排序结束后,
检验位置p上的值是1还是0,来继续调整下一次二分。直到二分结束后即
可。复杂度为O(mlog2n)。
此题好像为河北省省赛题。
For Algorithm: 整体二分,线段树维护,yy乱搞,意志力
Code
#include <cstdio>#include <iostream>#include <cmath>#include <cstring>#include <algorithm>#define fo(i,a,b) for (int i=a;i<=b;i++)#define fd(i,a,b) for (int i=a;i>=b;i--) #define N 100005using namespace std;int n,m,tree[N*4],Flag[N*4],q;bool Mark[N];struct note{ int x,l,r,op;}a[N];inline int read(int &n){ char ch=' ';int q=0,w=1; for(;(ch!='-')&&((ch<'0')||(ch>'9'));ch=getchar()); if(ch=='-')w=-1,ch=getchar(); for(;ch>='0' && ch<='9';ch=getchar())q=q*10+ch-48;n=q*w;return n;}void Build(int v,int l,int r){ Flag[v]=-1; int mid=(l+r)>>1; if (l==r) { tree[v]=Mark[l]; return; } Build(v*2,l,mid); Build(v*2+1,mid+1,r); tree[v]=tree[v*2]+tree[v*2+1];}void Color(int v,int l,int r,int x) {tree[v]=(r-l+1)*x; Flag[v]=x;}void Pushdown(int v,int l,int r){ int mid=(l+r)>>1; Color(v*2,l,mid,Flag[v]); Color(v*2+1,mid+1,r,Flag[v]); Flag[v]=-1;}void Change(int v,int l,int r,int x,int y,int z){ if (x>y) return; if (x<=l && y>=r) { Color(v,l,r,z); return; } int mid=(l+r)>>1; if (Flag[v]!=-1) Pushdown(v,l,r); if (x<=mid) Change(v*2,l,mid,x,y,z); if (y>mid) Change(v*2+1,mid+1,r,x,y,z); tree[v]=tree[v*2]+tree[v*2+1];}int Query(int v,int l,int r,int x,int y){ if (x<=l && y>=r) return tree[v]; if (Flag[v]!=-1) Pushdown(v,l,r); int mid=(l+r)>>1,sum=0; if (x<=mid) sum+=Query(v*2,l,mid,x,y); if (y>mid) sum+=Query(v*2+1,mid+1,r,x,y); return sum;}bool Pd(int x){ fo(i,1,n) Mark[i]=(a[i].x<x); Build(1,1,n); fo(i,1,m) { int sum=Query(1,1,n,a[i].l,a[i].r); if (a[i].op==0) { Change(1,1,n,a[i].l,a[i].l+sum-1,1); Change(1,1,n,a[i].l+sum,a[i].r,0); } else { Change(1,1,n,a[i].l,a[i].r-sum,0); Change(1,1,n,a[i].r-sum+1,a[i].r,1); } } return Query(1,1,n,q,q)==0;}int main(){ read(n);read(m); fo(i,1,n) read(a[i].x); fo(i,1,m) read(a[i].op),read(a[i].l),read(a[i].r); read(q); int l=1,r=n,ans=0; while (l<r) { int mid=(l+r)>>1; if (Pd(mid)) ans=max(ans,mid),l=mid+1; else r=mid; } printf("%d\n",ans); return 0;}
0 0
- 【NOIP2016模拟7.11】排序
- 【NOIP2016模拟7.11】排序
- JZOJ 4605 排序【NOIP2016模拟7.11】
- 【bzoj4552】【Tjoi2016&Heoi2016】【NOIP2016模拟7.12】排序
- 【NOIP2016提高A组模拟9.14】排序
- 重庆市noip2016模拟round4 BSOJ4874 排序
- 【bzoj4551】【NOIP2016模拟7.11】树
- 【NOIP2016模拟7.11】树 题解+代码
- JZOJ 4604 树【NOIP2016模拟7.11】
- JZOJ 4606 序列【NOIP2016模拟7.11】
- 【NOIP2016模拟7.12】游戏
- 树[NOIP2016模拟]
- 【NOIP2016模拟7.8】Stree
- NOIP2016模拟赛 day6
- noip2016模拟赛day7
- 【NOIP2016】蚯蚓 --队列模拟
- NOIP2016模拟 游戏 搜索
- NOIP2016模拟 JackMa 贪心
- iOS 日历
- CentOs7下GitHub入门复习
- java之多态的类型
- Genymotion模拟器在Android Studio上的安装
- MFC中程序的延时
- 【NOIP2016模拟7.11】排序
- elasticsearch 分布式
- java之StringBuffer常见功能
- poj3277city,离散化+线段树 或 stl的multiset
- docker
- Web Storage
- java之流与文件
- 文章标题
- java之String类--获取判断转换替换切割除空比较