题目链接:

Counting Intersections

Time Limit: 12000/6000 MS (Java/Others)  

  Memory Limit: 65536/65536 K (Java/Others)

Problem Description
Given some segments which are paralleled to the coordinate axis. You need to count the number of their intersection.

The input data guarantee that no two segments share the same endpoint, no covered segments, and no segments with length 0.

 
Input
The first line contains an integer T, indicates the number of test case.

The first line of each test case contains a number n(1<=n<=100000), the number of segments. Next n lines, each with for integers, x1, y1, x2, y2, means the two endpoints of a segment. The absolute value of the coordinate is no larger than 1e9.

 
Output
For each test case, output one line, the number of intersection.
 
Sample Input
2
4
1 0 1 3
2 0 2 3
0 1 3 1
0 2 3 2
4
0 0 2 0
3 0 3 2
3 3 1 3
0 3 0 2
 
Sample Output
4
0
题意:
 
求这些与坐标轴平行的线段的交点有多少个;
 
思路:
 
差不多就是原来的一道CF的原题,传送门
交点的个数就是每个线段覆盖的点数的和减去所有线段覆盖的点,而所有的线段覆盖的点数就可以用扫描线算法变成求面积;
 
AC代码:
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N=1e5+4;
int n,x1,x2,y3,y2,rec[2*N],num;
struct no
{
int l,r,h,flag;
};
no line[8*N];
struct nod
{
int l,r,cover;
ll sum;
};
nod tree[8*N];
int cmp(no x,no y)
{
return x.h<y.h;
}
void build(int node,int L,int R)
{
tree[node].l=L,tree[node].r=R;
tree[node].cover=tree[node].sum=0;
if(L>=R)return ;
int mid=(L+R)>>1;
build(2*node,L,mid);
build(2*node+1,mid+1,R);
}
void Pushup(int node)
{
if(tree[node].cover)
{
tree[node].sum=rec[tree[node].r+1]-rec[tree[node].l];
}
else
{
if(tree[node].l==tree[node].r)tree[node].sum=0;
else tree[node].sum=tree[2*node].sum+tree[2*node+1].sum;
}
}
void update(int node,int L,int R,int x)
{
if(L<=tree[node].l&&R>=tree[node].r)
{
tree[node].cover+=x;
Pushup(node);
return ;
}
int mid=(tree[node].l+tree[node].r)>>1;
if(L>mid) update(2*node+1,L,R,x);
else if(R<=mid)update(2*node,L,R,x);
else
{
update(2*node,L,mid,x);
update(2*node+1,mid+1,R,x);
}
Pushup(node);
}
int bi(int x)
{
int L=1,R=num-1,mid;
while(L<=R)
{
mid=(L+R)>>1;
if(rec[mid]==x)return mid;
else if(rec[mid]>x)R=mid-1;
else L=mid+1;
}
return -1;
}
int main()
{
int t;
scanf("%d",&t);
while(t--)
{
scanf("%d",&n);
ll sum=0;
int cnt=1;
for(int i=1;i<=n;i++)
{
scanf("%d%d%d%d",&x1,&y3,&x2,&y2);
if(x1>x2)swap(x1,x2);
if(y3>y2)swap(y3,y2);
rec[cnt] = line[cnt].l = x1;
line[cnt].r = x2+1;
line[cnt].h = y3;
line[cnt++].flag = 1;
line[cnt].l = x1;
rec[cnt] = line[cnt].r = x2+1;
line[cnt].h = y2+1;
line[cnt++].flag = -1;
if(x1==x2)sum=sum+abs(y2-y3)+1;
else sum=sum+abs(x1-x2)+1;
}
sort(line+1,line+cnt,cmp);
sort(rec+1,rec+cnt);
num = 2;
for(int i = 2;i < cnt;i++)
{
if(rec[i]!=rec[i-1])rec[num++]=rec[i];
}
build(1,1,num-1);
ll ans=0;
for(int i = 1;i < cnt-1;i++)
{
int fx = bi(line[i].l);
int fy = bi(line[i].r)-1;
if(fx <= fy)
{
update(1,fx,fy,line[i].flag);
}
ans+=tree[1].sum*(ll)(line[i+1].h-line[i].h);
}
// cout<<ans<<endl;
//cout<<sum<<" ";
printf("%lld\n",sum-ans);
}
return 0;
}

  

hdu-5862 Counting Intersections(线段树+扫描线)的更多相关文章

  1. HDU 5862 Counting Intersections(离散化+树状数组)

    HDU 5862 Counting Intersections(离散化+树状数组) 题目链接http://acm.split.hdu.edu.cn/showproblem.php?pid=5862 D ...

  2. HDU 5862 Counting Intersections (树状数组)

    Counting Intersections 题目链接: http://acm.split.hdu.edu.cn/showproblem.php?pid=5862 Description Given ...

  3. Hdu 5862 Counting Intersections(有n条线段,每一条线段都是平行于x轴或者y轴,问有多少个交点+树状数组区间求和单点跟新)

    传送门:Hdu 5862 Counting Intersections 题意:有n条线段,每一条线段都是平行于x轴或者y轴,问有多少个交点 分析: 基本的操作流程是:先将所有的线段按照横树坐标x按小的 ...

  4. hdu 5862 Counting Intersections

    传送门:hdu 5862 Counting Intersections 题意:对于平行于坐标轴的n条线段,求两两相交的线段对有多少个,包括十,T型 官方题解:由于数据限制,只有竖向与横向的线段才会产生 ...

  5. HDU 5862 Counting Intersections 扫描线+树状数组

    题目链接: http://acm.split.hdu.edu.cn/showproblem.php?pid=5862 Counting Intersections Time Limit: 12000/ ...

  6. HDU 1828“Picture”(线段树+扫描线求矩形周长并)

    传送门 •参考资料 [1]:算法总结:[线段树+扫描线]&矩形覆盖求面积/周长问题(HDU 1542/HDU 1828) •题意 给你 n 个矩形,求矩形并的周长: •题解1(两次扫描线) 周 ...

  7. hdu 1828 Picture(线段树扫描线矩形周长并)

    线段树扫描线矩形周长并 #include <iostream> #include <cstdio> #include <algorithm> #include &l ...

  8. HDU 6096 String 排序 + 线段树 + 扫描线

    String Time Limit: 6000/3000 MS (Java/Others) Memory Limit: 524288/524288 K (Java/Others) Problem De ...

  9. HDU 5862 Counting Intersections (离散化+扫描线+树状数组)

    题意:给你若干个平行于坐标轴的,长度大于0的线段,且任意两个线段没有公共点,不会重合覆盖.问有多少个交点. 析:题意很明确,可是并不好做,可以先把平行与x轴和y轴的分开,然后把平行y轴的按y坐标从小到 ...

随机推荐

  1. shell脚本实现定时重启进程

    ##############################Deploy crontab for yechang ad*******eta restart ###################### ...

  2. C语言的空格问题

    对于C语言中,一般的理解是对于空格,我们可以随意输入,因为空格没啥大意义,但是事实上并非如此. 1.'\'空格的问题 '\' 字符可用于一些字符进行转移,当然也包括了 newline(enter),被 ...

  3. 1M网速等于多少K

    http://zhidao.baidu.com/question/157400316.html&__bd_tkn__=65ac453b343794385019e962bfb06bb8c710d ...

  4. 将web工程部署到tomcat

    http://blog.csdn.net/lucklq/article/details/7621807 http://jingyan.baidu.com/article/466506582f2f4af ...

  5. Continuously Integrate

     Continuously Integrate David Bartlett THE Build AS A "Big BAng" EvEnT in project develop ...

  6. 基于EasyNVR二次开发实现业务需求:用户、权限、设备管理

    许多接触到EasyNVR的用户.开发者都会提出关于EasyNVR设备分组和账户设备关系映射的问题,我们参考目前大部分的视频能力输出平台的做法,EasyNVR目前只做了唯一的用户/密码(类比appkey ...

  7. Hibernate的配置文件 Hibernate.cfg.xml与xxx.hbm.xml

    1.hibernate.cfg.xml配置如下: (数据库连接配置) <?xml version="1.0" encoding="UTF-8"?>& ...

  8. Channel (digital image) 通道 色彩深度 Color_depth

    en.wikipedia.org/wiki/Channel_(digital_image) Color digital images are made of pixels, and pixels ar ...

  9. 题解 CF97C 【Winning Strategy】

    题解 CF97C [Winning Strategy] 此题是某平台%你赛原题,跟大家分享一下某校zsy和sxr等同学的神仙做法. 我解释一下题意,大是说,我有[无限]个人,每个人可以对他" ...

  10. ABAP excel操作 OLE 常用方法和属性

    转自 http://bstone.blog.163.com/blog/static/176820446201172834149199/#userconsent# OLE 常用方法和属性 1.ole中如 ...