hdu5107 K-short Problem 离线,离散化,线段树
2015-08-22 01:12
369 查看
题意:给出n栋楼的坐标和高度,询问<=x,<=y的第k高的楼的高度,(k<=10).
parse:离线处理,对y坐标离散化,把楼和询问按x排序,每询问到x将<=x的楼加入线段树中,线段树维护y坐标的前10,这时就可以查询1-y的第k高,二维转一维。
parse:离线处理,对y坐标离散化,把楼和询问按x排序,每询问到x将<=x的楼加入线段树中,线段树维护y坐标的前10,这时就可以查询1-y的第k高,二维转一维。
#include<iostream> #include<cstring> #include<cstdio> #include<ostream> #include<istream> #include<algorithm> #include<queue> #include<string> #include<cmath> #include<set> #include<map> #include<stack> #include<vector> #define fi first #define se second #define pii pair<int,int> #define ll long long #define inf 1000000009; #define eps 1e-8 using namespace std; const int maxn=30005; int n,m; struct Node { int x,y,w; int id; bool operator<(const Node& u)const { if(x==u.x) return id<u.id; return x<u.x; } }; Node d[maxn]; Node q[maxn]; int y[maxn*2]; int cnt; int h[maxn<<3][15]; int we[maxn]; int e; int ans[maxn]; void pushUp(int rt) { int tmp[30]; for(int i=1;i<=10;i++) { tmp[i]=h[rt<<1][i]; tmp[i+10]=h[rt<<1|1][i]; } sort(tmp+1,tmp+21); for(int i=1;i<=10;i++) h[rt][i]=tmp[i]; } void update(int l,int a,int L,int R,int rt) { if(l==L&&l==R) { for(int i=1;i<=10;i++) { if(a<h[rt][i]) { h[rt][i]=a; break; } } return; } int m=(L+R)/2; if(l<=m) update(l,a,L,m,rt<<1); else update(l,a,m+1,R,rt<<1|1); pushUp(rt); } void query(int l,int r,int k,int L,int R,int rt) { if(l<=L&&r>=R) { for(int i=1;i<=k;i++) { we[e++]=h[rt][i]; } return; } int m=(L+R)/2; if(l<=m) query(l,r,k,L,m,rt<<1); if(r>m) query(l,r,k,m+1,R,rt<<1|1); } int main() { int a,b,c; while(~scanf("%d%d",&n,&m)) { for(int i=1;i<=(n+m)*4;i++) { for(int j=1;j<=10;j++) h[i][j]=inf; } cnt=0; for(int i=1;i<=n;i++) { scanf("%d%d%d",&d[i].x,&d[i].y,&d[i].w); d[i].id=i; y[cnt++]=d[i].y; } for(int i=1;i<=m;i++) { scanf("%d%d%d",&q[i].x,&q[i].y,&q[i].w); y[cnt++]=q[i].y; q[i].id=i; } sort(y,y+cnt); int k=unique(y,y+cnt)-y; for(int i=1;i<=n;i++) { d[i].y=lower_bound(y,y+k,d[i].y)-y+1; } for(int i=1;i<=m;i++) { q[i].y=lower_bound(y,y+k,q[i].y)-y+1; } sort(d+1,d+n+1); sort(q+1,q+m+1); int kk=1; for(int i=1;i<=m;i++) { while(kk<=n && d[kk].x<=q[i].x) { update(d[kk].y,d[kk].w,1,n+m,1); kk++; } e=0; query(1,q[i].y,q[i].w,1,n+m,1); sort(we,we+e); int op=we[q[i].w-1]; if(op==1000000009) op=-1; ans[q[i].id]=op; } for(int i=1;i<=m;i++) printf("%d\n",ans[i]); } return 0; }
相关文章推荐
- DocFetcher CMD 启动脚本
- 图集name='imgurls' 判断
- Linux编译安装mysql
- LeetCode Evaluate Reverse Polish Notation
- LeetCode Evaluate Reverse Polish Notation
- JQuery实现回车代替Tab键(按回车跳到下一栏)
- Android屏幕自适应解决办法
- 文章标题
- Facade外观模式
- [LeetCode#216]Combination Sum III
- 数据库集群
- MapReduce Job 全局共享数据
- SPOJ 10628 Count on a tree (lca+主席树)
- 版本问题的坑
- HDU 2094 产生冠军(水题 map使用)
- POJ 1663 解题报告
- HDU 5414 CRB and String(贪心)
- 线程自动加锁与自动解锁:lock_guard & unique_lock
- IOS Storybroad和纯代码界面互联
- jQuery插件开发精品教程