【发布时间】:2016-12-18 02:14:10
【问题描述】:
我试图了解我计算堪培拉距离时发生了什么。我编写了自己的简单canberra.distance 函数,但结果与dist 函数不一致。我在我的函数中添加了选项na.rm = T,以便能够在分母为零时计算总和。从?dist 我了解到他们使用类似的方法:Terms with zero numerator and denominator are omitted from the sum and treated as if the values were missing.
canberra.distance <- function(a, b){
sum( (abs(a - b)) / (abs(a) + abs(b)), na.rm = T )
}
a <- c(0, 1, 0, 0, 1)
b <- c(1, 0, 1, 0, 1)
canberra.distance(a, b)
> 3
# the result that I expected
dist(rbind(a, b), method = "canberra")
> 3.75
a <- c(0, 1, 0, 0)
b <- c(1, 0, 1, 0)
canberra.distance(a, b)
> 3
# the result that I expected
dist(rbind(a, b), method = "canberra")
> 4
a <- c(0, 1, 0)
b <- c(1, 0, 1)
canberra.distance(a, b)
> 3
dist(rbind(a, b), method = "canberra")
> 3
# now the results are the same
0-0 和 1-1 对似乎有问题。在第一种情况 (0-0) 中,分子和分母都等于 0,应该省略这对。在第二种情况下(1-1),分子为 0,但分母不是,则项也为 0,总和不应改变。
我在这里错过了什么?
编辑:
为了符合R定义,函数canberra.distance可以修改如下:
canberra.distance <- function(a, b){
sum( abs(a - b) / abs(a + b), na.rm = T )
}
但是,结果和以前一样。
【问题讨论】:
-
我认为您可能偶然发现了基础 R 中的一个错误。我不确定,但 Wolfram Alpha agrees with you。不幸的是,我找不到权威参考,但根据 Wikipedia 和 Wolfram,您的实现似乎是正确的。
-
事实上,documentation of
dist将堪培拉距离定义为 sum(|x_i - y_i| / |x_i + y_i|)(这与您和 Wolfram 的不同)。它还指出“[t]his 旨在用于非负值(例如计数):取分母的绝对值是 1998 R 修改以避免负距离。” — 所以 R 的定义被证明是不同的。 -
@KonradRudolph 感谢您的回复!我编辑了我的帖子。使用 R 定义的堪培拉距离不一致仍然存在,所以我认为这不是问题。
-
是的,我怀疑文档中提到的“1998 R 修改”不仅仅是删除负值。实际上,文档可能旨在说明“此实现以未指定的方式不同于其他定义,因此产生不同的结果”。查看 C 源代码可以澄清这一点。无论如何,至少它的记录很差。