距离
欧氏距离
二维空间
定义
欧氏距离,一般也称作欧几里得距离。在平面直角坐标系中,设点
解释
举个例子,若在平面直角坐标系中,有两点
除此之外,
n 维空间
引入
那么,三维空间中两点的欧氏距离公式呢?我们来观察下图。
我们很容易发现,在
定义
由此可得,三维空间中欧氏距离的距离公式为:
解释
NOIP2017 提高组 奶酪 就运用了这一知识,可以作为欧氏距离的例题。
以此类推,我们就得到了
欧氏距离虽然很有用,但也有明显的缺点。两个整点计算其欧氏距离时,往往答案是浮点型,会存在一定误差。
曼哈顿距离
定义
在二维空间内,两个点之间的曼哈顿距离(Manhattan distance)为它们横坐标之差的绝对值与纵坐标之差的绝对值之和。设点
解释
观察下图:
在
同样的例子,在下图中
通过公式,我们很容易得到
经过推导,我们得到
性质
除了公式之外,曼哈顿距离还具有以下数学性质:
-
非负性
曼哈顿距离是一个非负数。
-
统一性
点到自身的曼哈顿距离为
。 -
对称性
到 与 到 的曼哈顿距离相等,且是对称函数。 -
三角不等式
从点
到 的直接距离不会大于途经的任何其它点 的距离。
例题
根据题意,对于式子
只要分别求出
=== "C++"
```cpp
#include <bits/stdc++.h>
using namespace std;
int main() {
int n, x, y, minx = 0x7fffffff, maxx = 0, miny = 0x7fffffff, maxy = 0;
scanf("%d", &n);
for (int i = 1; i <= n; i++) {
scanf("%d%d", &x, &y);
minx = min(minx, x + y), maxx = max(maxx, x + y);
miny = min(miny, x - y), maxy = max(maxy, x - y);
}
printf("%d\n", max(maxx - minx, maxy - miny));
return 0;
}
```
=== "Python"
```python
minx = 0x7fffffff; maxx = 0; miny = 0x7fffffff; maxy = 0
n = int(input())
for i in range(1, n + 1):
x, y = map(lambda x:int(x), input().split())
minx = min(minx, x + y); maxx = max(maxx, x + y)
miny = min(miny, x - y); maxy = max(maxy, x - y)
print(max(maxx - minx, maxy - miny))
```
其实还有第二种做法,那就是把曼哈顿距离转化为切比雪夫距离求解,最后部分会讲到。
切比雪夫距离
定义
切比雪夫距离(Chebyshev distance)是向量空间中的一种度量,二个点之间的距离定义为其各坐标数值差的最大值。1
在二维空间内,两个点之间的切比雪夫距离为它们横坐标之差的绝对值与纵坐标之差的绝对值的最大值。设点
解释
仍然是这个例子,下图中
曼哈顿距离与切比雪夫距离的相互转化
过程
首先,我们考虑画出平面直角坐标系上所有到原点的曼哈顿距离为
通过公式,我们很容易得到方程
将绝对值展开,得到
将这
正方形边界上所有的点到原点的 曼哈顿距离 都是
同理,我们再考虑画出平面直角坐标系上所有到原点的 切比雪夫距离 为
通过公式,我们知道
我们将式子展开,也同样可以得到可以得到
画到平面直角坐标系上,可以得到一个边长为
正方形边界上所有的点到原点的切比雪夫距离都是
将这两幅图对比,我们会神奇地发现:
这
证明
所以,曼哈顿距离与切比雪夫距离之间会不会有联系呢?
接下来我们简略证明一下:
假设
我们把曼哈顿距离中的绝对值拆开,能够得到四个值,这四个值中的最大值是两个非负数之和,即曼哈顿距离。则
我们很容易发现,这就是
所以将每一个点
同理,
而这就是
所以将每一个点
结论
- 曼哈顿坐标系是通过切比雪夫坐标系旋转
后,再缩小到原来的一半得到的。 - 将一个点
的坐标变为 后,原坐标系中的曼哈顿距离等于新坐标系中的切比雪夫距离。 - 将一个点
的坐标变为 后,原坐标系中的切比雪夫距离等于新坐标系中的曼哈顿距离。
碰到求切比雪夫距离或曼哈顿距离的题目时,我们往往可以相互转化来求解。两种距离在不同的题目中有不同的优缺点,应该灵活运用。
例题
P4648「IOI2007」pairs 动物对数(曼哈顿距离转切比雪夫距离)
P3964「TJOI2013」松鼠聚会(切比雪夫距离转曼哈顿距离)
最后给出 P5098「USACO04OPEN」Cave Cows 3 的第二种解法:
我们考虑将题目所求的曼哈顿距离转化为切比雪夫距离,即把每个点的坐标
所求的答案就变为
现要使得横坐标之差和纵坐标之差最大,只需要预处理出
=== "C++"
```cpp
#include <bits/stdc++.h>
using namespace std;
int main() {
int n, x, y, a, b, minx = 0x7fffffff, maxx = 0, miny = 0x7fffffff, maxy = 0;
scanf("%d", &n);
for (int i = 1; i <= n; i++) {
scanf("%d%d", &a, &b);
x = a + b, y = a - b;
minx = min(minx, x), maxx = max(maxx, x);
miny = min(miny, y), maxy = max(maxy, y);
}
printf("%d\n", max(maxx - minx, maxy - miny));
return 0;
}
```
=== "Python"
```python
minx = 0x7fffffff; maxx = 0; miny = 0x7fffffff; maxy = 0
n = int(input())
for i in range(1, n + 1):
a, b = map(lambda x:int(x), input().split())
x = a + b; y = a - b
minx = min(minx, x); maxx = max(maxx, x)
miny = min(miny, y); maxy = max(maxy, y)
print(max(maxx - minx, maxy - miny))
```
对比两份代码,我们又能够发现,两种不同的思路,写出来的代码却是完全等价的,是不是很神奇呢?当然,更高深的东西需要大家另行研究。
距离
一般地,我们定义平面上两点
特殊的,
汉明距离
汉明距离是两个字符串之间的距离,它表示两个长度相同的字符串对应位字符不同的数量
我们可以简单的认为对两个串进行异或运算,结果为 1 的数量就是两个串的汉明距离。
部分内容搬运自 浅谈三种常见的距离算法,感谢作者 xuxing 的授权。
参考资料
Footnotes
贡献者:@Menci@Jimmy@Ir1d@WenzelTian@XTh3G4p@InfinityLoop@Henry-ZHR@Shuhao@mgt@turing0@Chrogeek@Margatroid@ezoixx130@countercurrent_time@Haoshen@ouuan@Xeonacid@abc1763613206@Tiger3018
本页面最近更新:2/3/2023, 12:00:00 AM,更新历史
发现错误?想一起完善? 在 GitHub 上编辑此页!
本页面的全部内容在 CC BY-SA 4.0 和 SATA 协议之条款下提供,附加条款亦可能应用