地球表层/ dplyr:创建坐标之间距离的矩阵

5
我希望能够使用dplyr/geosphere创建多个坐标之间的“矩阵”距离。我已经看到geosphere包提供了这个功能。我成功地创建了两个向量之间的距离,但是我在创建完整矩阵时遇到了困难。
这是一个包含多个坐标的样本表格。
df <- data.frame(latitude = c(49.48609,-8.14671,11.28625),
                 longitude = c(8.463678,143.05793,-11.18285))

  latitude  longitude
1 49.48609   8.463678
2 -8.14671 143.057930
3 11.28625 -11.182850

我需要的输出结果如下:

  latitude    longitude    distance-latlon1    distance-latlon2   distance-latlon3                 
1 49.48609     8.463678    NA                  *latlon2><latlon1  *latlon3><latlon1
2 -8.14671   143.057930    *latlon1><latlon2   NA                 *latlon3><latlon2
3 11.28625   -11.182850    *latlon1><latlon3   *latlon2><latlon3  NA

我尝试使用geosphere,但我只找到了一种计算两列之间距离的方法(在这个片段中结果为0)。

library(geosphere) 
df$distance <- distVincentyEllipsoid(df[,c('longitude','latitude')],
                                     df[,c('longitude','latitude')])
3个回答

4
你需要使用geosphere包中的distm函数。使用方法如下:
# create a distance matrix
m <- distm(df[2:1], df[2:1], fun = distVincentyEllipsoid)

# replace the diagonal with NA
diag(m) <- NA

# make column names for the distance matrix
colnames(m) <- paste0('r',1:nrow(df))

# bind the distance matrix to the dataframe
cbind.data.frame(df, m)

你将得到:

  latitude  longitude       r1       r2       r3
1 49.48609   8.463678       NA 13792423  4606658
2 -8.14671 143.057930 13792423       NA 17189185
3 11.28625 -11.182850  4606658 17189185       NA

2

我会建议使用更快更准确的distGeo,而不是distVincentyEllipsoid


df = df[,2:1] # the order should be longitude, latitude!
distm(df, df, distGeo)

最初的回答
或者
library(raster)
d <- pointDistance(df)

"最初的回答" 可能会跟在

段落标签后面。

as.matrix(as.dist(d))

0
我们可以使用sf包中的st_distance函数,该函数使用geosphere中的函数来计算距离,如果sf对象是以经纬度(EPSG 4326)投影的。 df2是示例输出。
# Load packages
library(dplyr)
library(sf)

# Create example data frame
df <- data.frame(latitude = c(49.48609,-8.14671,11.28625),
                 longitude = c(8.463678,143.05793,-11.18285))

# COnvert to sf object
df_sf <- st_as_sf(df, coords = c("longitude", "latitude"))

# Set the projection as ESPG 4326 (long_lat)
st_crs(df_sf) <- 4326

# Apply the st_distance function
dist_m <- st_distance(df_sf)

# Combine with df
df2 <- df %>%
  mutate(`distance-latlon1` = as.numeric(dist_m[, 1]), 
         `distance-latlon2` = as.numeric(dist_m[, 2]),
         `distance-latlon3` = as.numeric(dist_m[, 3])) 

# Replace 0 with NA
df2[df2 == 0] <- NA

df2
  latitude  longitude distance-latlon1 distance-latlon2 distance-latlon3
1 49.48609   8.463678               NA         13792423          4606658
2 -8.14671 143.057930         13792423               NA         17189185
3 11.28625 -11.182850          4606658         17189185               NA

这里有一种将dist_mdf结合的替代方法。

library(tidyr)

# Convert dist_m to data frame
dist_df <- dist_m %>%
  as.table() %>%
  as_data_frame() %>%
  spread(Var2, n) %>%
  select(-Var1) %>%
  mutate_all(as.numeric) %>%
  setNames(paste0("distance-latlon", 1:nrow(df)))

# Combine with df
df2 <- df %>%
  bind_cols(dist_df)

# Replace 0 with NA
df2[df2 == 0] <- NA

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接