数星星(单点更新,求前缀和)
http://acm.hdu.edu.cn/showproblem.php?pid=1541
题意:二维平面坐标上,给出n个星星的坐标,规定每个星星的左下方向的星星数量为该星星的等级。
统计1-n-1等级的数量。
解法:因为给出顺序的特殊性,可以用树状数组统计各星星的等级。
注意两点:1、该题为多组输入(该题没讲。。没有就T)
2、坐标范围从0开始,而树状数组一般从一开始,所以将坐标都加一。
//#include <bits/stdc++.h> #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> #include <iostream> #include <cstdio> #include <string> #include <stdio.h> #include <queue> #include <stack> #include <map> #include <set> #include <string.h> #include <vector> #define ME(x , y) memset(x , y , sizeof(x)) #define SF(n) scanf("%d" , &n) #define rep(i , n) for(int i = 0 ; i < n ; i ++) #define INF 0x3f3f3f3f #define mod 1000000007 #define PI acos(-1) using namespace std; typedef long long ll ; int x[15009] , y[15009]; int xm ; int ans[15009]; int c[32009]; int lowerbit(int x) { return x&(-x) ; } void add(int x , int val) { for(int i = x ; i <= xm ; i += lowerbit(i)) { c[i] += val ; } } int getsum(int x) { int ans = 0 ; for(int i = x ; i >= 1 ; i -= lowerbit(i)) { ans += c[i]; } return ans ; } int main() { int n ; while(~scanf("%d" , &n)) { memset(c , 0 , sizeof(c)); memset(ans , 0 , sizeof(ans)); for(int i = 0 ; i < n ; i++) { scanf("%d%d" , &x[i] , &y[i]); x[i]++; xm = max(x[i] , xm) ; } int sum = 0 ; for(int i = 0 ; i < n ; i++) { sum = getsum(x[i]); add(x[i] , 1); ans[sum]++ ; } for(int i = 0 ; i < n ; i++) { cout << ans[i] << endl ; } } return 0 ; }