【问题标题】:R: Faster way of computing large distance matrixR:计算大距离矩阵的更快方法
【发布时间】:2016-05-24 07:30:06
【问题描述】:

我正在计算球体上大量位置 (5000) 之间的距离矩阵(使用 Haversine 距离函数)。

这是我的代码:

require(geosphere)
x=rnorm(5000)
y=rnorm(5000)
xy1=cbind(x,y)

计算距离矩阵的时间为

 system.time( outer(1:nrow(xy1), 1:nrow(xy1), function(i,j) distHaversine(xy1[i,1:2],xy1[j,1:2])))

执行此程序所需的时间很长。任何建议如何降低完成这项工作的时间!谢谢。

【问题讨论】:

  • 您可以尝试另一种实现方式。见r-bloggers.com/…
  • @Leo 良心良心,无意冒犯我必须指出链接的文章是糟糕!作者使用for循环循环一个向量来重复调用一个已经vectorized的函数(distHaversine())!!他们编写了 更多 代码,同时还将执行速度降低了大约 300 倍!!!不要看这篇文章!你不会调用一个函数 10,000 次,而一次就可以了!
  • 嗨@SimonO'Hanlon,感谢您的提醒。 :-)

标签: r geosphere


【解决方案1】:

试试geosphere包中的内置函数?

z <- distm( xy1 )

distm() 的默认距离函数 - 计算一组点之间的距离矩阵 - 是 Haversine ("distHaversine") 公式,但您可以使用 fun 参数指定另一个。

在我的 2.6GHz Core i7 rMBP 上,这需要大约 5 秒才能获得 5,000 分。

【讨论】:

  • 感谢您的建议。这次执行所用的时间不到我的代码的一半。
【解决方案2】:

我在下面添加了一个使用 spatialrisk 包的解决方案。此包中的关键函数是用 C++ (Rcpp) 编写的,因此速度非常快。

library(geosphere)
library(spatialrisk)
library(data.table)

x=rnorm(5000)
y=rnorm(5000)
xy1 = data.table(x,y)

# Cross join two data tables
coordinates_dt <- optiRum::CJ.dt(xy1, xy1)

system.time({
  z <- distm( xy1 )
})
# user  system elapsed 
# 14.163   3.700  19.072 

system.time({
  distances_m <- coordinates_dt[, dist_m := spatialrisk::haversine(y, x, i.y, i.x)]
})
# user  system elapsed 
# 2.027   0.848   2.913 

【讨论】:

    猜你喜欢
    • 2021-10-26
    • 1970-01-01
    • 1970-01-01
    • 2017-11-15
    • 1970-01-01
    • 2014-09-24
    • 2018-08-05
    • 1970-01-01
    相关资源
    最近更新 更多