算法:曼哈顿距离转切比雪夫距离+并查集+平衡树
(这里的代码选择STL里的set实现平衡树)
储备知识
曼哈顿距离
在二维空间内,两个点之间的曼哈顿距离为它们横坐标之差的绝对值与纵坐标之差的绝对值之和。设点 A(x1,y1),B(x2,y2),则 A,B 之间的曼哈顿距离用公式可以表示为:
dAB=|x1-x2|+|y1-y2|
通过公式,我们很容易得到 A,B两点间的曼哈顿距离:
dAB=|6-2|+|5-2|=4+3=7
切比雪夫距离
在二维空间内,两个点之间的切比雪夫距离为它们横坐标之差的绝对值与纵坐标之差的绝对值的最大值。设点 A(x1,y1),B(x2,y2),则 A,B 之间的切比雪夫距离用公式可以表示为:
dAB=max(|x1-x2|,|y1-y2|)
通过公式,我们很容易得到 A,B两点间的切比雪夫距离:
dAB=max(|6-2|,|5-2|)=max(4,3)=4
二维曼哈顿距离与切比雪夫距离的相互转化
设A(x1,Y1),B(x2,y2),A,B两点的曼哈顿距离为:
dAB=|x1-x2|+|y1-y2|
=max{x1-x2+y1-y2,x1-x2+y2-y1,x2-x1+y1-y2,x2-x1+y2-y1}
=max{|(x1+y1)-(x2+y2)|,|(x1-y1)-(x2-y2)|}
很容易发现,这就是 (x1 + y1,x1- y1), (x2 + y2,x2 - y2) 两点之间的切比雪夫距离。
这样,我们就把两点间的曼哈顿距离转化成了切比雪夫距离。
set
STL中很重要的一种容器!!!不会的自行百度学习!!!
题目
题面描述
了解奶牛们的人都知道,奶牛喜欢成群结队.观察约翰的N(1≤N≤100000)只奶牛,你会发现她们已经结成了几个“群”.
每只奶牛在吃草的时候有一个独一无二的位置坐标Xi,Yi(l≤Xi,Yi≤[1~109];Xi,Yi∈整数.
当满足下列两个条件之一,两只奶牛i和j是属于同一个群的:
1.两只奶牛的曼哈顿距离不超过C(1≤C≤109),即lXi - Xjl+IYi- Yjl≤C.
2.两只奶牛有共同的邻居.即,存在一只奶牛k,使i与k,j与k均同属一个群.
给出奶牛们的位置,请计算草原上有多少个牛群,以及最大的牛群里有多少奶牛?
输入
第1行:N和C;
接下来N行:每行输入一只奶牛的坐标.
输出
输出仅一行,先输出牛群数,再输出最大牛群里的牛数,用空格隔开.
解题思路
先将A(x1,Y1),B(x2,y2)两点的曼哈顿距离:|x1-x2|+|y1-y2|按上述知识转化为 (x1 + y1,x1- y1), (x2 + y2,x2 - y2) 两点之间的切比雪夫距离:max{|(x1+y1)-(x2+y2)|,|(x1-y1)-(x2-y2)|}。
设X=x+y,Y=x-y,现在只要保证max{△X,△Y}<C,既保证△X<C且△Y<C即可。
先将转化后的所有点按X排序,维护△X<c,不满足则指针now右移。然后对Y维护平衡树,如果当前点与其前驱后继的△Y<C,则用并查集将它们合并在一起(即放在一个牛群中)。
具体细节请看代码中注释!!!
代码演示
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<set>
#define inf 10000000000LL
using namespace std;