uva 1428 Ping pong (树状数组)
2014-10-19 11:31
483 查看
题意:
一条街道上有N个选手,他们要打乒乓球赛,每个人有一个自己的skill rank,且是N个不同的数。每场比赛需要一个裁判,要求这个裁判的skill rank不能高于也不能低于这两个选手,且在街上住的位置必须在两个选手之间。问可以组织多少场比赛。
开始想到了可以用树状数组处理每个人前面有多少sr(skill rank)大于他的。但是开始想法是枚举起止点开中间有多少符合要求的裁判,是N方的。看了刘汝佳白书才知道正确做法是枚举中间的裁判。
对于裁判i,假设我们知道他之前sr小于他的人数Front【i】,和之后sr大于他的人数Back【i】。
那么他能组织的比赛数量就是Front【i】*Back【i】+(i-1-Front【i】)*(N-i-Back【i】) (左小右大和左大右小)
这样O(n)遍历一遍就行了。
求Front【i】,Back【i】的方法和求逆序数一样。
求出Front【i】后求Back【i】不需要重新排序,清空c数组后从后往前再做一遍,但因为遍历是从后到前,而查询还是从前往后的。所以做的时候把需要+1的位置ord修改为N-i-ord就可以了。
代码:
一条街道上有N个选手,他们要打乒乓球赛,每个人有一个自己的skill rank,且是N个不同的数。每场比赛需要一个裁判,要求这个裁判的skill rank不能高于也不能低于这两个选手,且在街上住的位置必须在两个选手之间。问可以组织多少场比赛。
开始想到了可以用树状数组处理每个人前面有多少sr(skill rank)大于他的。但是开始想法是枚举起止点开中间有多少符合要求的裁判,是N方的。看了刘汝佳白书才知道正确做法是枚举中间的裁判。
对于裁判i,假设我们知道他之前sr小于他的人数Front【i】,和之后sr大于他的人数Back【i】。
那么他能组织的比赛数量就是Front【i】*Back【i】+(i-1-Front【i】)*(N-i-Back【i】) (左小右大和左大右小)
这样O(n)遍历一遍就行了。
求Front【i】,Back【i】的方法和求逆序数一样。
求出Front【i】后求Back【i】不需要重新排序,清空c数组后从后往前再做一遍,但因为遍历是从后到前,而查询还是从前往后的。所以做的时候把需要+1的位置ord修改为N-i-ord就可以了。
代码:
#include <iostream> #include <cstdio> #include <cstring> #include <algorithm> using namespace std; #define LL long long struct node{ int num,ord; }G[20010]; int a[20010]; int c[20010]; int Front[20010]; int Back[20010]; int N; int lowbit(int n){ return n&(-n); } int sum(int p){ int res=0; while(p<=N){ res+=c[p]; p+=lowbit(p); } return res; } void add(int p,int n){ while(p>0){ c[p]+=n; p-=lowbit(p); } } bool cmp(node a,node b){ if(a.num==b.num) return a.ord<b.ord; return a.num<b.num; } int main(){ int T; scanf("%d",&T); while(T--){ scanf("%d",&N); memset(c,0,sizeof(c)); for(int i=1;i<=N;i++){ scanf("%d",&G[i].num); G[i].ord=i; } sort(G+1,G+N+1,cmp); for(int i=1;i<=N;i++){ Front[i]=sum(G[i].ord); add(G[i].ord,1); } memset(c,0,sizeof(c)); for(int i=N;i>=1;i--){ int pos=N-G[i].ord+1; Back[i]=sum(pos); add(pos,1); } long long res=0; for(int i=1;i<=N;i++){ res+=Front[i]*Back[i]; res+=(N-i-Back[i])*(i-1-Front[i]); } printf("%lld\n",res); } return 0; }
相关文章推荐
- UVA 1428 Ping Pong(树状数组)
- uva 1428 - Ping pong(树状数组)
- UVA 1428 - Ping pong(树状数组)
- Beijing 2008 / UVa 1428 / POJ 3928 / HDU 2492 Ping pong (树状数组)
- uva 1428 - Ping pong(树状数组,4级)
- uva 1428 - Ping pong(树状数组,4级)
- UVA1428 Ping pong(树状数组)
- UVA1428 Ping pong(树状数组)
- UVA1428 - Ping pong(树状数组)
- UVA-1428 - Ping pong(树状数组)
- UVA1428 Ping pong(树状数组)
- uva 1428 - Ping pong (树状数组的应用)
- UVA 1428 - Ping pong(树状数组)
- uva 1428 - Ping pong(树状数组)
- [树状数组]Ping Pong, Beijing 2008, Uva1428
- 【uva】1428 - Ping pong(树状数组)
- UVA 1428 - Ping pong(树状数组)
- Uva 1428 Ping pong (树状数组,Fenwick树)
- UVa:1428 Ping pong (树状数组)
- uvalive 4329 Ping pong (树状数组)