zoukankan      html  css  js  c++  java
  • poj 3067 Japan 【树状数组】

    <题目链接>

    题目大意:

    有两个点集,这两个点集从上至下分别从1~n,1~m编号,现在给出n组数据,(x,y),表示左边点集编号为x的点与右边点集编号为y的点相连,现在要求计算这些线段的交点个数。

    解题分析:

    先将这些线段的x变量从小到大排序,若x相同,再将y从小到大排序。然后就可以直接遍历这些线段了,同时对y变量建一维树状数组,利用sum(m)-sum(node[i].y)可以很容易求出之前插入的所有线段的y值中,有多少线段的y值大于当前插入的y值,这一步相当于对排好序的线段的y值进行逆序数的求解,因为之前插入线段的x必然小于等于当前线段的x值,所以这些y值还大于node[i].y的线段必然会与当前线段产生一个交点。

     1 #include <cstdio>
     2 #include <cstring>
     3 #include <algorithm>
     4 using namespace std;
     5 
     6 typedef long long ll;
     7 const int M =1e6+10;
     8 int n,m,k;
     9 int tr[M]; 
    10 struct NODE{
    11     int x,y;
    12     bool operator <(const NODE &tmp)const{    
    13         if(x==tmp.x)return y<tmp.y;
    14         else return x<tmp.x;
    15     }
    16 }node[M];
    17 inline int lowbit(int x){return x&(-x);}
    18 void add(int i,int val){
    19     while(i<=m){
    20         tr[i]+=val;
    21         i+=lowbit(i);
    22     }
    23 }
    24 int sum(int i){
    25     ll ans=0;
    26     while(i>0){
    27         ans+=tr[i];
    28         i-=lowbit(i);
    29     }
    30     return ans;
    31 }
    32 int main(){
    33     int T,ncase=0;
    34     scanf("%d",&T);
    35     while(T--){
    36         scanf("%d%d%d",&n,&m,&k);
    37         for(int i=1;i<=k;i++){
    38             scanf("%d%d",&node[i].x,&node[i].y);
    39         }
    40         sort(node+1,node+1+k);    
    41         memset(tr,0,sizeof(tr));
    42         ll ans=0;
    43         for(int i=1;i<=k;i++){
    44             ans+=sum(m)-sum(node[i].y);  //sum(m)表示之前插入所有线段的个数,sum(node[i],y)表示之前插入的所有y值小于等于node[i].y的线段个数,因此sum(m)-sum(node[i].y)求得的是之前插入的y值中,比当前node[i].y大的线段的个数
    45             //因为在该数之前插入树状数组的x值都小于等于当前线段的x值,所以这样可以求出所有线段相交的个数。
    46             add(node[i].y,1);
    47         }
    48         printf("Test case %d: %lld
    ",++ncase,ans);
    49     }
    50     return 0;
    51 }

    2018-10-17

  • 相关阅读:
    FastDFS迁移步骤
    Centos7 单节点安装 FastDFS + FastDHT服务
    CentOS 7.0 上安装和配置 VNC 服务器
    Ubuntu 18.04 安装 Xfce桌面和VNC的方法
    Ubuntu 16.04设置root用户登录图形界面
    Windows批量查找文件
    WIN10打开网络共享文件夹提示0x80004005怎么解决?(转载)
    ack 工具
    win7/win10 未分配磁盘怎样创建扩展分区 也就是逻辑分区(转截)
    [bzoj4842][bzoj1283][Neerc2016]Delight for a Cat/序列_线性规划_费用流
  • 原文地址:https://www.cnblogs.com/00isok/p/9804155.html
Copyright © 2011-2022 走看看