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
分析:对于横向线段只保留两个端点并记录类型,对竖向线段保留整个线段;
   离散化并排序,遍历竖向线段,对横向端点树状数组更新;
代码:
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cmath>
#include <algorithm>
#include <climits>
#include <cstring>
#include <string>
#include <set>
#include <map>
#include <queue>
#include <stack>
#include <vector>
#include <list>
#define rep(i,m,n) for(i=m;i<=n;i++)
#define rsp(it,s) for(set<int>::iterator it=s.begin();it!=s.end();it++)
#define mod 1000000007
#define inf 0x3f3f3f3f
#define vi vector<int>
#define pb push_back
#define mp make_pair
#define fi first
#define se second
#define ll long long
#define pi acos(-1.0)
#define pii pair<int,int>
#define Lson L, mid, rt<<1
#define Rson mid+1, R, rt<<1|1
const int maxn=2e5+;
const int dis[][]={{,},{-,},{,-},{,}};
using namespace std;
ll gcd(ll p,ll q){return q==?p:gcd(q,p%q);}
ll qpow(ll p,ll q){ll f=;while(q){if(q&)f=f*p;p=p*p;q>>=;}return f;}
int n,m,k,t,x[maxn],y[maxn],p[maxn],xcnt,ycnt,id,idx;
ll ans;
multiset<int>s;
struct node
{
int x,low,high;
bool operator<(const node&p)const
{
return x<p.x;
}
}a[maxn];
struct node1
{
int x,y,type;
bool operator<(const node1&p)const
{
return x<p.x;
}
}g[maxn];
int get(int x)
{
int sum=;
for(int i=x;i;i-=(i&(-i)))
sum+=p[i];
return sum;
}
void add(int x,int y)
{
for(int i=x;i<=maxn-;i+=(i&(-i)))
p[i]+=y;
}
int main()
{
int i,j;
scanf("%d",&t);
while(t--)
{
xcnt=ycnt=id=idx=;
ans=;
memset(p,,sizeof(p));
scanf("%d",&n);
rep(i,,n)
{
int b,c,d,e;
scanf("%d%d%d%d",&b,&c,&d,&e);
if(c>e)swap(c,e);
if(b>d)swap(b,d);
if(b==d)
{
x[++xcnt]=a[++id].x=b;
y[++ycnt]=a[id].low=c;
y[++ycnt]=a[id].high=e;
}
else
{
x[++xcnt]=b;
x[++xcnt]=d;
y[++ycnt]=c;
g[++idx].x=b;
g[idx].y=c;
g[idx].type=;
g[++idx].x=d;
g[idx].y=e;
g[idx].type=;
}
}
sort(x+,x+xcnt+);
sort(y+,y+ycnt+);
sort(a+,a+id+);
sort(g+,g+idx+);
int num1=unique(x+,x+xcnt+)-x-;
int num2=unique(y+,y+ycnt+)-y-;
rep(i,,id)
{
a[i].x=lower_bound(x+,x+num1+,a[i].x)-x;
a[i].low=lower_bound(y+,y+num2+,a[i].low)-y;
a[i].high=lower_bound(y+,y+num2+,a[i].high)-y;
}
rep(i,,idx)
{
g[i].x=lower_bound(x+,x+num1+,g[i].x)-x;
g[i].y=lower_bound(y+,y+num2+,g[i].y)-y;
}
int now=;
rep(i,,id)
{
while(now<=idx&&g[now].x<=a[i].x)
{
if(g[now].type==)add(g[now].y,);
else {
if(g[now].x!=a[i].x)
add(g[now].y,-);
else s.insert(g[now].y);
}
now++;
}
ans+=get(a[i].high)-get(a[i].low-);
for(int x:s)add(x,-);
s.clear();
}
printf("%lld\n",ans);
}
//system("Pause");
return ;
}

Counting Intersections的更多相关文章

  1. hdu 5862 Counting Intersections

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

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

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

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

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

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

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

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

    Counting Intersections Time Limit: 12000/6000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/ ...

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

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

  7. hdu-5862 Counting Intersections(线段树+扫描线)

    题目链接: Counting Intersections Time Limit: 12000/6000 MS (Java/Others)     Memory Limit: 65536/65536 K ...

  8. 2016暑假多校联合---Counting Intersections

    原题链接 Problem Description Given some segments which are paralleled to the coordinate axis. You need t ...

  9. 【HDU5862】Counting Intersections

    题意 有n条线段,且都平行于坐标轴.对于每条线段,给出两个端点的坐标.问一共有多少个线段的交点. 分析 最最简单的扫描法了.用线段树或者树状数组都可以. 由题目可知,线段只有两种,要么平行于x轴要么平 ...

随机推荐

  1. Linux raid信息 查看

    Linux下查看软.硬raid信息的方法. 软件raid:只能通过Linux系统本身来查看 cat /proc/mdstat 可以看到raid级别,状态等信息. 硬件raid: 最佳的办法是通过已安装 ...

  2. 解析JSON对象与字符串之间的相互转换

    在开发的过程中,如果对于少量参数的前后台传递,可以直接采用ajax的data函数,按json格式传递,后台Request即可,但有的时候,需要传递多个参数,这样后台 接受的时候Request多个很麻烦 ...

  3. rndc 错误解决 和 远程配置

    dc: connect failed: connection refusedrndc: connect failed: connection refused 解决办法:默认安装BIND9以后,是无法直 ...

  4. curl 测试web站点的响应时间

    curl -s -w "\n"::%{time_namelookup}::%{time_connect}::%{time_starttransfer}::%{time_total} ...

  5. 【单源最短路】dijstra poj 1502

    #include <cstdio> #include <iostream> #include <stdlib.h> #include <memory.h> ...

  6. selenium和pythond的区别

    selenium和pythond的区别 天宇6169 | 浏览 137 次 2016-03-18 10:25 2016-03-18 12:24 最佳答案   selenium ide是用来录制的!大概 ...

  7. python smtplib.SMTPDataError: (554

  8. Ubuntu下载工具 uget+aria2

    一.安装. uget和aria2都可以在“软件中心”中安装,但是版本太老啦,无法发挥作用,所以最好还是在终端中添加ppa进行安装: 1.uget的安装:  sudo add-apt-repositor ...

  9. 转: JMeter技巧集锦

    from:http://java.chinaitlab.com/tools/355421.html JMeter 是一个流行的用于负载测试的开源工具, 具有许多有用的功能元件,如线程组(thread ...

  10. mysql 查询 45 道题

    一.            设有一数据库,包括四个表:学生表(Student).课程表(Course).成绩表(Score)以及教师信息表(Teacher).四个表的结构分别如表1-1的表(一)~表( ...