HDU 4417 超级马里奥 数据结构+利用树状数组进行快速统计+多维统计转换
2016-08-03 15:01
417 查看
HDU 4417 超级马里奥
Time Limit:1000MS Memory Limit:32768KB 64bit IO Format:%I64d & %I64u
SubmitStatusPracticeHDU
4417
Description
马里奥是一个举世闻名的管道工,他的跳跃能力让我们钦佩。在一条长度为n的道路上,在每个整数点i的位置都有一个高度为hi的障碍物。现在的问题是:假设马里奥可以跳跃的最高高度为H,在道路的[L,R]
区间内他可以跳跃过的障碍物有多少个(不要考虑他被挡住)?
Input
第一行是数据个数T。
对于每组数据:
第一行包含两个整数n, m (1 <= n <=10^5, 1 <= m <= 10^5), n
表示道路的程度, m是询问的个数.
第二行包含n个整数,表示每个障碍物的高度,
高度范围是 [0, 1000000000].
接着 m 行,每行3个整数 L, R,H.( 0 <= L <= R < n 0 <= H <= 1000000000.)
Output
对于每组数据, 先输出"Case X: " (
X表示组数) 然后有m行,
每行包含一个整数. 第i个整数表示第i个询问的答案。
4000
Sample Input
Sample Output
Time Limit:1000MS Memory Limit:32768KB 64bit IO Format:%I64d & %I64u
SubmitStatusPracticeHDU
4417
Description
马里奥是一个举世闻名的管道工,他的跳跃能力让我们钦佩。在一条长度为n的道路上,在每个整数点i的位置都有一个高度为hi的障碍物。现在的问题是:假设马里奥可以跳跃的最高高度为H,在道路的[L,R]
区间内他可以跳跃过的障碍物有多少个(不要考虑他被挡住)?
Input
第一行是数据个数T。
对于每组数据:
第一行包含两个整数n, m (1 <= n <=10^5, 1 <= m <= 10^5), n
表示道路的程度, m是询问的个数.
第二行包含n个整数,表示每个障碍物的高度,
高度范围是 [0, 1000000000].
接着 m 行,每行3个整数 L, R,H.( 0 <= L <= R < n 0 <= H <= 1000000000.)
Output
对于每组数据, 先输出"Case X: " (
X表示组数) 然后有m行,
每行包含一个整数. 第i个整数表示第i个询问的答案。
4000
Sample Input
1 10 10 0 5 2 7 5 4 3 8 7 7 2 8 6 3 5 0 1 3 1 1 9 4 0 1 0 3 5 5 5 5 1 4 6 3 1 5 7 5 7 3
Sample Output
Case 1: 4 0 0 3 1 2 0 1 5 1 解题思路: 这题是一个利用树状数组或线段树进行快速统计的一个题,题目不难但是不是很好想起来 比赛的时候没有想起来,简直被自己蠢哭了,唉。 1,首先这是一个经典的统计问题,求区间内小于某个数的个数有多少 2,这是一个二维统计问题,有两个变量需要考虑一个是区间,另一个是高度 3,因为区间不好通过排序消除影响,所以就是通过高度的排序消除高度的影响了 4,把询问的高度按照从小到大排序,顺序取出每一个高度h,然后把这条路上的所有的小于 这个高度的填充进(树状数组或线段树)对应的下标那里加一,然后对于h的查询就很好算了 5,简单统计一定要想到这种做法。。。。 下面代码用的树状数组。
#include<cstdio> #include<algorithm> #include<iostream> #include<algorithm> #include<cstring> using namespace std; #define lson l , m , rt << 1 #define rson m + 1 , r , rt << 1 | 1 const int maxn = 100005; int n ; struct node{ int id; int x ; int y ; int h ; int num; }; node arry[maxn] ; int C[maxn] ; struct node2{ int id; int h ; }; node2 s[maxn] ; int lowbit(int x){return x&-x;} int sum(int x){ int ret = 0 ; while(x>0){ ret+=C[x]; x-=lowbit(x); //printf("shgfaj"); //printf("ret = %d\n",ret); } //printf("ret = %d\n",ret); return ret ; } void add(int x,int d){ while(x<=n){ C[x]+=d ; x+=lowbit(x) ; //printf("asd"); } return ; } bool cmp(node a,node b){ return a.h<b.h ; } bool cmp2(node a,node b){ return a.id<b.id ; } bool cmp3(node2 a,node2 b){ return a.h<b.h ; } int main() { int m; int T ,cas=1; //freopen("in.txt","r",stdin); scanf("%d",&T); while(T--){ scanf("%d%d",&n,&m); for(int i=1;i<=n;i++){ scanf("%d",&s[i].h); s[i].id = i ; } for(int i=1;i<=m;i++){ scanf("%d%d%d",&arry[i].x,&arry[i].y,&arry[i].h); arry[i].x++ ; arry[i].y++ ; arry[i].id = i ; } sort(arry+1,arry+m+1,cmp) ; sort(s+1,s+n+1,cmp3); // for(int i=1;i<=m;i++){ // printf("%d ",arry[i].h); // }printf("\n"); // for(int i=1;i<=m;i++){ // printf("%d ",s[i].h); // }printf("\n"); memset(C,0,sizeof(C)); int j=1; for(int i=1;i<=m;i++){ for(;j<=n&&s[j].h<=arry[i].h;j++){ add(s[j].id,1); //printf("id = %d\n",s[j].id); } //printf("i = %d\n",i); int as = sum(arry[i].y) ; //printf("sssss = %d\n",as); arry[i].num = sum(arry[i].y)-sum(arry[i].x-1) ; } //printf("max = %d\n",sum(n)); sort(arry+1,arry+m+1,cmp2) ; printf("Case %d:\n",cas++); for(int i=1;i<=m;i++){ printf("%d\n",arry[i].num); } } return 0; }
相关文章推荐
- 数据结构基础_对一个数组进行升序排序
- HDU 4417 Super Mario 第37届ACM/ICPC 杭州赛区网络赛1008题(树状数组或者线段树)
- 数据结构之树状数组
- 【数据结构之树状数组】
- HDU 4417 Super Mario--离线树状数组、划分树、线段树
- 数据结构之树状数组
- 利用数组进行数据查找
- 算法笔记五:利用堆结构来对数据进行排序
- hdu 4417 离线树状数组
- hdu 4417 树状数组 离线处理
- hdu 4417 Super Mario(划分树或树状数组)
- C#自动给据sql中的带@的变量提取变量名称在从简单数据对象中取得生成SqlParameter数组进行数据插入(利用反射完成)
- hdu 4417 离线树状数组 胡乱搞搞
- HDU 4417 —— Super Mario(树状数组,离散化,离线处理)
- .net 利用array.sort对结构数组进行排序
- 利用Etherape对网络拓扑结构和数据流量进行实时监控
- 如何利用php数组对百万数据进行排重
- 数据结构之树状数组
- [HDU 4417] Super Mario (树状数组)
- HDU 4417 Super Mario(离线线段树or树状数组)