M.J的blog

algorithm,ACM-ICPC
随笔 - 39, 文章 - 11, 评论 - 20, 引用 - 0
数据加载中……

POJ 3067 Japan【树状数组】

这道题和那道Star如出一辙,可我还是做了很长时间 ...太菜了...有K条连接东西两个城市的路,东西方向每个城市都有一个编号M,N,从北到南,最后问共有多少个十字路都,即有多少个交点。
先预处理,用结构体表示每条边,对结构体按N进行从小到大的排序,如果N相同,按M从小到大排序。接下来就和Star一样了,唯一不同的是Star那道题是每次求出当前星星前边的个数,而这个是求当前点后边的个数。用c[]表示树状数组,sum(n)求出的是N编号小于等于n的city的个数,只需每次拿出一个city,求出N编号大于它的city的个数,然后更新数组就可以了。
 关键代码:
1 long long ans=0;
2 for(i=1;i<=K;i++){                       //K表示边的个数
3     ans+=sum(max)-sum(a[i].east);        //east即为N编号
4     modify(a[i].east,1);                 //将a[i].east插入到当前数组
5 }
6 
解决了这一步,其余就是套路了,很简单。
Code:
 1 #include<iostream>
 2 #include<algorithm>
 3 #define MAX 10005                      //最大的city个数
 4 using namespace std;
 5 int c[MAX],n,N,M,K,omax;
 6 struct road
 7 {
 8     int west,east;
 9 }a[MAX*MAX];                            //MAX*MAX为最多的边的个数
10 bool cmp(road a,road b){                
11     if(a.west==b.west)
12         return a.east<b.east;
13     return a.west<b.west;
14 }
15 int lowbit(int t){
16     return t&(t^(t-1));
17 }
18 int sum(int t){
19     int total=0;
20     while(t>0){
21         total+=c[t];
22         t-=lowbit(t);
23     }
24     return total;
25 }
26 void modify(int posi,int key){
27     while(posi<=omax){
28         c[posi]+=key;
29         posi+=lowbit(posi);
30     }
31 }
32 int main()
33 {
34     int i,j,k,m,cas;
35     long long ans;
36     scanf("%d",&cas);
37     for(i=1;i<=cas;++i){
38         omax=0;                                //用omax表示所有east的最大值,以确定求和区间
39         memset(c,0,sizeof(c));
40         scanf("%d%d%d",&N,&M,&K);
41         for(j=1;j<=K;++j){
42             scanf("%d%d",&a[j].east,&a[j].west);
43             if(a[j].east>omax)
44                 omax=a[j].east;
45         }
46         sort(a+1,a+1+K,cmp);
47         ans=0;
48         for(j=1;j<=K;++j){                        //key code
49             ans+=(sum(omax)-sum(a[j].east));
50             modify(a[j].east,1);
51         } 
52         printf("Test case %d: %lld\n",i,ans);
53     }
54 }
55 

posted on 2010-05-02 18:18 M.J 阅读(735) 评论(1)  编辑 收藏 引用 所属分类: 树状数组

评论

# re: POJ 3067 Japan【树状数组】  回复  更多评论   

很好
2010-07-23 21:48 | kajf

只有注册用户登录后才能发表评论。
网站导航: 博客园   IT新闻   BlogJava   知识库   博问   管理