poj2828Buy Tickets
来源:互联网 发布:知乎必须用手机注册吗 编辑:程序博客网 时间:2024/05/21 14:46
题目大意:
有N个人排队买票,每个人都能差一次队,现在将这些人的插队次序和查完队后站在他前面的人数告诉你,要求你输出最后的次序。
解题思路:
非常经典巧妙的题目,竟然可以用线段树来搞。
本题主要解决的问题是如何根据插入的顺序重写队列次序,(这个时候我又想说只可意会不可言传了。)既然前面的位置会不断的被后来位置给跟新了,那我如果从后面开始向前面插的话,位置肯定是可以一步步的都确定了,如果碰到前面的与后面的位置相同的话就只能往后面插了。(挺别扭,自己慢慢体会吧~~)
#include<stdio.h>#define N 200009int pos[N],val[N],op[N],tree[N<<2];void build(int rt,int l,int r)//建树,节点表示该节点的空位置的数目{ tree[rt]=r-l+1; if(l==r) return; int mid=(l+r)>>1; build(rt<<1,l,mid); build(rt<<1|1,mid+1,r);}int insert(int rt,int l,int r,int pre)//插入{ tree[rt]--; if(l==r) return l; int mid=(l+r)>>1; if(tree[rt<<1]>=pre)//能往前插就往前插 return insert(rt<<1,l,mid,pre); else { pre-=tree[rt<<1]; return insert(rt<<1|1,mid+1,r,pre);//往右插 }}int main(){ int n,i,j; while(scanf("%d",&n)!=EOF){ build(1,1,n); i=n; for(i=1;i<=n;i++) { scanf("%d%d",&pos[i],&val[i]); } for(i=n;i>0;i--){ j=insert(1,1,n,pos[i]+1); op[j]=val[i]; } printf("%d",op[1]); for(i=2;i<=n;i++) printf(" %d",op[i]); printf("\n"); }}
0 0
- poj2828Buy Tickets
- poj2828Buy Tickets
- poj2828Buy Tickets
- poj2828Buy Tickets
- poj2828Buy Tickets
- poj2828Buy Tickets segment_tree
- poj2828Buy Tickets【线段树】
- POJ2828Buy Tickets(AC)
- POJ2828Buy Tickets(线段树)
- poj2828Buy Tickets(线段树,每次插入后把余下的看作是一个新的集合)
- poj 2182 Lost Cows 暴力或者用线段树 + poj2828Buy Tickets
- Tickets
- Tickets
- Tickets
- Tickets
- p2346_Lucky Tickets
- lucky tickets
- Buy Tickets
- 微信封杀微软“小冰”的真相
- 《Java并发编程实战》第十五章 原子变量与非阻塞同步机制 读书笔记
- DOM方式解析xml文件查看天气
- 46. 谷歌面试题:寻找丑数
- 在windows下把tcl编译为exe程序
- poj2828Buy Tickets
- easy to understander characterise resistent
- LeetCode: Binary Tree Level Order Traversal II [107]
- Android输入法扩展之远程输入法
- 升了osx10.10后cocoapods用不了的解决方法
- 【足迹C++primer】19、构造函数再探
- Android自动化测试初探(一): 捕获Activity上的Element
- 自学第六天
- LeetCode: Convert Sorted Array to Binary Search Tree [108]