首页 > 解决方案 > 查找每个组内最近的地理点

问题描述

我正在尝试为每个“年”组中的每家银行找到最近的点(在我的情况下是最近的银行)。我曾尝试使用 st_distance,但没有成功。

这是我的数据示例:

   Year                   geometry                                 bank   Location
7  1838   POINT (759859.6 -728345)                       Bank of Mobile     Mobile
43 1838 POINT (779861.1 -445454.7)         Bank of the State of Alabama Tuscaloosa
58 1838 POINT (819114.6 -285180.1) Bank of the State of Alabama, branch    Decatur
59 1841 POINT (819114.6 -285180.1) Bank of the State of Alabama, branch    Decatur
60 1842 POINT (819114.6 -285180.1) Bank of the State of Alabama, branch    Decatur
67 1838 POINT (853709.4 -267830.7) Bank of the State of Alabama, branch Huntsville
68 1841 POINT (853709.4 -267830.7) Bank of the State of Alabama, branch Huntsville
69 1842 POINT (853709.4 -267830.7) Bank of the State of Alabama, branch Huntsville
79 1838   POINT (759859.6 -728345) Bank of the State of Alabama, branch     Mobile
91 1838 POINT (905601.7 -526517.9) Bank of the State of Alabama, branch Montgomery

我想做的是知道,例如,分别在 1838 年、1841 年和 1842 年的“迪凯特”中,离“阿拉巴马州银行分行”最近的银行是哪家。

对于某些银行,与另一家银行的最小距离应该为零,因为在同一个城镇/城市中有几家银行(例如 1838 年的“移动银行”)。


这是一个可重现的示例:

  S1 <- structure(list(Year = c("1838", "1838", "1838", "1841", "1842", 
    "1838", "1841", "1842", "1838", "1838", "1841", "1842", "1838"
    ), geometry = structure(list(structure(c(759859.587499541, -728344.968108917
    ), class = c("XY", "POINT", "sfg")), structure(c(779861.05153977, 
    -445454.703808866), class = c("XY", "POINT", "sfg")), structure(c(819114.617375314, 
    -285180.101652618), class = c("XY", "POINT", "sfg")), structure(c(819114.617375314, 
    -285180.101652618), class = c("XY", "POINT", "sfg")), structure(c(819114.617375314, 
    -285180.101652618), class = c("XY", "POINT", "sfg")), structure(c(853709.422752713, 
    -267830.684434561), class = c("XY", "POINT", "sfg")), structure(c(853709.422752713, 
    -267830.684434561), class = c("XY", "POINT", "sfg")), structure(c(853709.422752713, 
    -267830.684434561), class = c("XY", "POINT", "sfg")), structure(c(759859.587499541, 
    -728344.968108917), class = c("XY", "POINT", "sfg")), structure(c(905601.700907393, 
    -526517.946820037), class = c("XY", "POINT", "sfg")), structure(c(759859.587499541, 
    -728344.968108917), class = c("XY", "POINT", "sfg")), structure(c(759859.587499541, 
    -728344.968108917), class = c("XY", "POINT", "sfg")), structure(c(336877.092499058, 
    -301769.66275037), class = c("XY", "POINT", "sfg"))), class = c("sfc_POINT", 
    "sfc"), precision = 0, bbox = structure(c(xmin = 336877.092499058, 
    ymin = -728344.968108917, xmax = 905601.700907393, ymax = -267830.684434561
    ), class = "bbox"), crs = structure(list(epsg = NA_integer_, proj4string = "+proj=aea +lat_1=29.5 +lat_2=45.5 +lat_0=37.5 +lon_0=-96 +x_0=0 +y_0=0 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=m +no_defs"), class = "crs"), n_empty = 0L), 
    bank = c("Bank of Mobile", "Bank of the State of Alabama", 
    "Bank of the State of Alabama, branch", "Bank of the State of Alabama, branch", 
    "Bank of the State of Alabama, branch", "Bank of the State of Alabama, branch", 
    "Bank of the State of Alabama, branch", "Bank of the State of Alabama, branch", 
    "Bank of the State of Alabama, branch", "Bank of the State of Alabama, branch", "Planters & Merchants Bank", "Planters & Merchants Bank",
    "Bank of the State of Arkansas"), Location = c("Mobile", 
    "Tuscaloosa", "Decatur", "Decatur", "Decatur", "Huntsville", 
    "Huntsville", "Huntsville", "Mobile", "Montgomery", "Mobile", 
    "Mobile", "Little Rock")), sf_column = "geometry", agr = structure(c(Year = NA_integer_, 
    bank = NA_integer_, Location = NA_integer_), class = "factor", .Label = c("constant", 
    "aggregate", "identity")), row.names = c(7L, 43L, 58L, 59L, 60L, 
    67L, 68L, 69L, 79L, 91L, 116L, 117L, 130L), class = c("sf", "data.frame"
    ))

标签: rdistancespatial

解决方案


这是一个带有参数的函数,允许您按年份、银行名称和位置选择银行。它将返回一个sf具有该位置的对象以及距 data.frame 最近的位置,该位置来自同一年或以后的年份,但名称和位置不同。

您可能需要更改 index2 的逻辑,具体取决于您要查找的内容。

dist_by_year <- function(x = S1, year = 1841, 
                         bank = 'Bank of the State of Alabama, branch',
                         loc = 'Decatur'){
  x$Year <- as.numeric(x$Year)
  index1 <- which(x$bank == bank & x$Year == year & x$Location == loc)
  
  index2 <- which((x$bank != bank & x$Location != loc)& x$Year >= year )
  
  
  index3 <- st_nearest_feature(x[index1,], x[index2,])
  
  closest <- x[index2,][index3,]
  closest$id <- 'closest'
  target <- x[index1,]
  target$id <- 'target'
  rbind(closest, target)

}

回报:

> dist_by_year()
Simple feature collection with 2 features and 4 fields
geometry type:  POINT
dimension:      XY
bbox:           xmin: 759859.6 ymin: -728345 xmax: 819114.6 ymax: -285180.1
CRS:            +proj=aea +lat_1=29.5 +lat_2=45.5 +lat_0=37.5 +lon_0=-96 +x_0=0 +y_0=0 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=m +no_defs
    Year                                 bank Location      id                   geometry
116 1841            Planters & Merchants Bank   Mobile closest   POINT (759859.6 -728345)
59  1841 Bank of the State of Alabama, branch  Decatur  target POINT (819114.6 -285180.1)

可以通过管道传输到st_distance实际距离:

> dist_by_year() %>% st_distance()
Units: [m]
         [,1]     [,2]
[1,]      0.0 447108.8
[2,] 447108.8      0.0

推荐阅读