【问题标题】:Openstreetmap / iGraph - Create a center_bbox from center_bbox osmar object / make it efficientOpenstreetmap / iGraph - 从 center_bbox osmar 对象创建一个 center_bbox / 使其高效
【发布时间】:2020-10-08 11:10:15
【问题描述】:

调用get_osm(muc_bbox, src) 需要相当长的时间(46.151 秒)从一个大的 osm 文件加载。 我想知道是否可以根据需要从 center_bbox 创建一个 center_bbox?一次将大文件加载到内存中,然后根据要求从中创建小“盒子”?还是有不同的方法来解决这个问题?也许可以将大文件以不同的结构加载到内存中,并根据需要从中创建 bbox,这样总体上会更快? 我在这里上传了一个更大的 osm 文件OSM File

提前感谢您! BR。

library(osmar)
library(igraph)

### Get data ----
src <- osmsource_osmosis(file = "~/streets_bayern.osm")

muc_bbox <- center_bbox(11.575278, 48.137222, 41242.57, 41242.57)
muc <- get_osm(muc_bbox, src)

### Reduce to highways: ----
hways <- subset(muc, way_ids = find(muc, way(tags(k == "highway"))))
hways <- find(hways, way(tags(k == "name")))
hways <- find_down(muc, way(hways))
hways <- subset(muc, ids = hways)

#### Plot data ----
## Plot complete data and highways on top:
plot(muc)
plot_ways(muc, col = "lightgrey")
plot_ways(hways, col = "coral", add = TRUE)

### Define route start and end nodes: ----
id<-find(muc, node(tags(v %agrep% "Sendlinger Tor")))[1]
hway_start_node <-find_nearest_node(muc, id, way(tags(k == "highway"))) 
hway_start <- subset(muc, node(hway_start_node))

id <- find(muc, node(attrs(lon > 11.58 & lat > 48.15)))[1]
hway_end_node <- find_nearest_node(muc, id, way(tags(k == "highway")))
hway_end <- subset(muc, node(hway_end_node))

## Add the route start and and nodes to the plot:
plot_nodes(hway_start, add = TRUE, col = "red", pch = 19, cex = 2)
plot_nodes(hway_end, add = TRUE, col = "red", pch = 19, cex = 2)

### Create street graph ----
gr <- as.undirected(as_igraph(hways))

### Compute shortest route: ----
# Calculate route
route <- function(start_node,end_node) {
  get.shortest.paths(gr,
                     from = as.character(start_node),
                     to = as.character(end_node), 
                     mode = "all")[[1]][[1]]}
# Plot route

plot.route <- function(r,color) {
  r.nodes.names <- as.numeric(V(gr)[r]$name)
  r.ways <- subset(hways, ids = osmar::find_up(hways, node(r.nodes.names)))
  plot_ways(r.ways, add = TRUE, col = color, lwd = 2)
}




# Number of new ways to look for 
nways <- 10
# Weight factor applied to already found way
weightfactor <- 2


for (numway in 1:nways) {
  r <- route(hway_start_node,hway_end_node)
  color <- colorRampPalette(c("springgreen","royalblue"))(nways)[numway]
  plot.route(r,color)
  # Modify current route weight
  
  route_nodes <- as.numeric(V(gr)[r]$name)
  #We construct a newosmarobject containing only elements related to the nodes defining the route:
  route_ids <- find_up(hways, node(route_nodes))
  route_muc <- subset(hways, ids = route_ids)
  
  #Route details.
  #In order to present route details like street names,
  #distances, and directions we have to work directly on the internals of the osmar objects.
  #We start by extracting the route’s node IDs (which are in the correct order) and the way IDs (which we have to order)
  #where the nodes are members:
  
  node_ids <- route_muc$nodes$attrs$id
  
  # to delete node ids.
  # gr_muc<-delete_vertices(gr_muc, as.character(node_ids[20]))
  
  way_ids <- local({
    w <- match(node_ids, route_muc$ways$refs$ref)
    route_muc$ways$refs$id[w]
  })
  
  #Then we extract the names of the ways in the correct order:>
  way_names <- local({
    n <- subset(route_muc$ways$tags, k == "name")
    n[match(way_ids, n$id), "v"]
  })
  
  #The next step is to extract the nodes’ coordinates,>
  node_coords <- route_muc$nodes$attrs[, c("lon", "lat")]
  
  #and to compute the distances (meters) and the bearings (degrees) between successive nodes (using thepackagegeosphere):
  node_dirs <- local({
    n <- nrow(node_coords)
    from <- 1:(n - 1)
    to <- 2:n
    cbind(dist = c(0, distHaversine(node_coords[from,], node_coords[to,])),
          bear = c(0, bearing(node_coords[from,], node_coords[to,])))
  })
  
  #Finally, we pack together all the information, and additionally compute the cumulative distance
  #and a16-point compass rose direction (thecompass()function is available in the “navigator ” demo from theosmarpackage):
  
  route_details <- data.frame(way_names, node_dirs)
  route_details$cdist <- cumsum(route_details$dist)
  route_details$coord <- node_coords
  route_details$id <- node_ids
  print(route_details)
 

【问题讨论】:

    标签: r openstreetmap osmar


    【解决方案1】:

    您首先必须在您的计算机上使用downloadinstall Osmosis。
    以下脚本允许您定义一个框并查询您提供的大地图:

    library(osmar)
    
    # Set Osmosis source
    src <- osmsource_osmosis(file = here::here("streets_bayern.osm"))
    
    # Define box
    muc_bbox <- center_bbox(11.575278, 48.137222, 1000, 1000)
    
    # normally this should work, but didn't :
    # muc  <- get_osm(muc_bbox, src)
    
    # As I had trouble using directly get_osm, used modified source of it instead :
    destination <- tempfile(tmpdir = here::here(),pattern = "tmp",fileext=".tmp")
    request <- osmar:::osm_request(src, muc_bbox, destination)
    
    # Folder where Osmosis.bat is located
    osmosis.path <- 'c:/RDev/Osmosis/bin/'
    
    request <- paste0(osmosis.path,request)
    
    # Run request and check if it worked OK
    if (system(request)==127) {stop('Osmosis request failed')}
    
    # get response
    response <- readLines(destination)
    unlink(destination)
    
    # Parse response
    muc <- as_osmar(xmlParse(response))
    
    plot(muc)
    

    响应时间在 10 秒左右,比从 url 下载地图要快得多。

    【讨论】:

    • 非常感谢,但这不是问题所在。我想你想念我。我已经这样做了(见附件)。尝试定义一个更大的 bbox (40000x 40000) 并用 muc
    • 你的意思是什么都没发生吗?
    • 什么意思?我更改了代码以避免误解。加载此 bbox 需要 46.151 秒。如果我要加载整个巴伐利亚地图,它会变得更大。在那个大 bbox 中搜索路径会增加另一个漫长的等待时间,所以我需要能够从内存或其他结构中创建小的 bbox。
    • 在我的电脑上,加载 + 绘图脚本需要 11 秒(1000,1000),13 秒(2000,2000),18 秒(4000,4000)
    • OK : 终于明白 pb 了 :) as_osmar 函数占用了大部分时间
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-09-26
    • 2021-06-15
    • 1970-01-01
    • 2021-06-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多