poj3067 Japan(树状数组)

转载请注明出处:http://blog.csdn.net/u012860063

题目链接:http://poj.org/problem?id=3067


Description

Japan plans to welcome the ACM ICPC World Finals and a lot of roads must be built for the venue. Japan is tall island with N cities on the East coast and M cities on the West coast (M <= 1000, N <= 1000). K superhighways will be build. Cities on each coast
are numbered 1, 2, ... from North to South. Each superhighway is straight line and connects city on the East coast with city of the West coast. The funding for the construction is guaranteed by ACM. A major portion of the sum is determined by the number of
crossings between superhighways. At most two superhighways cross at one location. Write a program that calculates the number of the crossings between superhighways.

Input

The input file starts with T - the number of test cases. Each test case starts with three numbers – N, M, K. Each of the next K lines contains two numbers – the numbers of cities connected by the superhighway. The first one is the number of the city on the
East coast and second one is the number of the city of the West coast.

Output

For each test case write one line on the standard output:

Test case (case number): (number of crossings)

Sample Input

1
3 4 4
1 4
2 3
3 2
3 1

Sample Output

Test case 1: 5

Source

Southeastern Europe 2006

题意:日本岛东海岸与西海岸分别有N和M个城市,现在修高速公路连接东西海岸的城市,求交点个数。

做法:(做法的解释来自:http://blog.csdn.net/weiguang_123/article/details/7895848)记每条告诉公路为(x,y),
即东岸的第x个城市与西岸的第y个城市修一条路。当两条路有交点时,满足(x1-x2)*(y1-y2) < 0。所以,将每条路按x从小到达排序,若x相同,按y从小到大排序。 然后按排序后的公路用树状数组在线更新,求y的逆序数之 和 即为交点个数。

上面说的可能有点难理解,详细说明如下。

记第i条边的端点分别为xi,yi。

由于x是从小到大排序的,假设当前我们在处理第k条边,那么第1~k-1条边的x必然是小于(等于时候暂且不讨论)第k条边的 x 的,那么前k-1条边中,与第k条边相交的边的y值必然大于yk的,所以此时我们只需要求出在前k-1条边中有多少条边的y值在区间[yk, M]即可,也就是求yk的逆序数,M为西岸城市个数,即y的最大值。 所以就将问题转化成区间求和的问题,树状数组解决。当两条边的x相同时,我们记这两条边的y值分别为ya,yb(ya<yb),我们先处理(x,ya),再处理(x,yb),原因很明显,因为当x相同时,这两条边是认为没有交点的,若先处理(x,yb),那么下次处理(x,ya)时,(x,ya)就会给(x,yb)增加一个逆序,也就是将这两条边做相交处理了。

代码如下:

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
int n,m,k;
#define MAX 2047
struct node
{
	int l,r;//分别为左端点和右端点
}line[MAX*MAX];//高速公路的结构
int c[MAX];//树状数组
bool cmp( node a, node b)
{
	if(a.l==b.l)
	{
		return a.r<b.r;
	}
	return a.l<b.l;
}
int Lowbit(int x) // 2^k
{
	return x&(-x);
}
void update(int i, int x) //i点增量为x
{
	while(i <= m)
	{
		c[i] += x;
		i += Lowbit(i);
	}
}
__int64 sum(int x)
{
	__int64 sum=0;
	while(x > 0)
	{
		sum += c[x];
		x -= Lowbit(x);
	}
	return sum;
}
int main()
{
	int t, i;
	scanf("%d",&t);
	int tt=1;
	while(t--)
	{
		scanf("%d %d %d",&n,&m,&k);
		for(i = 1; i <= k; i++) //i须从1开始
		{
			scanf("%d%d",&line[i].l,&line[i].r);//输入
		}
		sort(line+1,line+k+1,cmp);//按照l的从小到大排序,l相同时按r的从小到大排序,
		//这样就形成了r的一维树状数组
		memset(c,0,sizeof(c));
		__int64 ret=0;//最后结果
		for(i = 1; i <= k; i++) //i须从1开始
		{
			update(line[i].r,1);//插入树状数组中
			ret+=i-sum(line[i].r);//i为当前已插入的元素的个数,getsum返回了小于等于当前r值的元素个数,
			//相减即为满足条件的元素个数
		}
		printf("Test case %d: %lld\n",tt++,ret);
	}
	return 0;
}

poj3067 Japan(树状数组)

时间: 2024-10-13 19:49:35

poj3067 Japan(树状数组)的相关文章

POJ3067 Japan 树状数组的应用

这题以前做过,用的线段树,现在用树状数组做一次, 题意:给你n个城市在日本左边,m个城市在日本右边,然后k条路,问你这k条路有几个交点,注意城市的序号其实就是一维坐标所在位置,所以就是两条平行的数轴,上面有点,而且之间有连线,问你有多少交点 一开始不好想把,这种题目也就排排序来试试看了,先对要修建的公路进行排序,然后再看这样是否可以更加方便的求出交点的数论,取路的左边点为先决条件从小到大排列,若相等则按照右边点来升序排列,然后以左边点为序号 和value值为1进行插入树状数组,先求出当前已经插入

POJ3067:Japan(树状数组求逆序对)

Description Japan plans to welcome the ACM ICPC World Finals and a lot of roads must be built for the venue. Japan is tall island with N cities on the East coast and M cities on the West coast (M <= 1000, N <= 1000). K superhighways will be build. C

POJ 3067 Japan (树状数组 &amp;&amp; 控制变量)

题意: 西海岸和东海岸有分别有n (1~n)个和m (1~m)个城市, 两个海岸的城市之间有k条公路连通, 公路会相交, 现在给出城市和公路的信息问你由这些公路组成的复杂交通有多少个交点 (如果两个条公路的起点或者终点相同那这两点不算做相交) 分析: 这里公路信息用(x, y)二元组来表示西海岸的x城市与东海岸的y城市相连, 首先自然想到给k个公路的信息按x或y排个序, 否则变量太乱不助于思考!先设想按x升序排序且先不管x相等的情况, 如果x是升序的, 那我在考虑第i条公路的时候是不是只要关心y

cdoj 383 japan 树状数组

Japan Time Limit: 1 Sec Memory Limit: 256 MB 题目连接 http://acm.uestc.edu.cn/#/problem/show/383 Description Japan plans to welcome the ACM ICPC World Finals and a lot of roads must be built for the venue. Japan is tall island with N cities on the East c

POJ 3067 Japan 树状数组求逆序对

题目大意:有两排城市,这两排城市之间有一些路相互连接着,求有多少条路相互交叉. 思路:把所有的路先按照x值从小到大排序,x值相同的按照y值从小到大排序,然后插入边的时候,先找有多少比自己y值小的,这些边的x值一定比自己大,也就是一个逆序对,然后统计起来.记得答案要用long long (__int64) CODE: #include <cstdio> #include <cstring> #include <iostream> #include <algorith

poj-3067 Japan(树状数组)

Description Japan plans to welcome the ACM ICPC World Finals and a lot of roads must be built for the venue. Japan is tall island with N cities on the East coast and M cities on the West coast (M <= 1000, N <= 1000). K superhighways will be build. C

POJ3067 Japan【树状数组】【逆序数】

题目链接: http://poj.org/problem?id=3067 题目大意: 有两排的城市,一排N个城市,编号为1~N,一排M个城市,编号为1~M.这两排城市之间有K条路. 路都是直线连接,问:这些路,有多少道路是相交的,并且焦点不是城市所在的点,求出交点个数. 思路: 树状数组的思想.参考网上的图,先将所有边(u,v)按u升序排列,如果u相同,则按v升序排列.可 以看出来,路(u1,v1)和路(u2,v2)如果有交点的话,u1 > u2 并且 v1 < v2,或者 u1 < u

(POJ 3067) Japan (慢慢熟悉的树状数组)

Japan Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 29295   Accepted: 7902 Description Japan plans to welcome the ACM ICPC World Finals and a lot of roads must be built for the venue. Japan is tall island with N cities on the East coas

UVALive-2926 Japan 【树状数组】

Description Japan plans to welcome the ACM ICPC World Finals and a lot of roads must be built for the venue. Japan is tall island with N cities on the East coast and M cities on the West coast (M 1000; N 1000). K superhighways will be build. Cities o