You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

OSMnx与NetworkX最短路径计算差异:path_OX_T为何未达预期?

关于OSMnx与NetworkX最短路径计算结果的疑问

尝试用多种方法计算最短路径时得到了不同结果(符合预期),但对每种方法的运行逻辑存疑。以法国安纳西(Annecy)为例,用NetworkX和OSMnx的Dijkstra算法得到了如下结果:

计算代码

import osmnx as ox
import networkx as nx

Cities = ['Annecy, France','Epagny Metz-Tessy, France']
graph_city = ox.graph_from_place(Cities, network_type='drive', simplify=True, truncate_by_edge=False, clean_periphery =True)
graph_city = ox.project_graph(graph_city)
graph_city = ox.consolidate_intersections(graph_city, rebuild_graph=True, tolerance=15, dead_ends=True)

graph_city = ox.add_edge_speeds(graph_city)
graph_city = ox.add_edge_travel_times(graph_city)

DEP_node = 530
ARR_node  = 549

path_NX = nx.dijkstra_path(graph_city, DEP_node, ARR_node)
path_OX_L = ox.shortest_path(graph_city, DEP_node, ARR_node, weight='length')
path_OX_T = ox.shortest_path(graph_city, DEP_node, ARR_node, weight='time')

fig, ax = ox.plot_graph_routes(graph_city, [path_NX,path_OX_L,path_OX_T], route_colors=['r','g','y'], route_linewidth=4,node_size=1, figsize=(7,7), bgcolor='#FFFFFF', node_color='#111111')

路径时间与长度统计代码

Time = int(sum(ox.utils_graph.get_route_edge_attributes(graph_city,path, 'travel_time')))
Length = int(sum(ox.utils_graph.get_route_edge_attributes(graph_city, path, 'length')))

计算结果

path_NXpath_OX_Lpath_OX_T
TIME238211238
LENGTH213619592136

可以看到,以length为权重通过OSMnx计算的path_OX_L不仅路径长度最短,耗时也更短。那本应追求最快的path_OX_T为何未达到预期效果?


问题原因分析

  1. NetworkX默认权重逻辑:
    nx.dijkstra_path未指定weight参数时,会优先使用边的weight属性;若图中无该属性,则每条边权重视为1。你的结果中path_NX与path_OX_T完全一致,说明图中默认的weight属性和travel_time等价,或者在图构建过程中weight被映射为旅行时间。

  2. path_OX_T未最优的核心原因:
    OSMnx的shortest_path指定weight='time'时,严格基于边的travel_time属性计算,但这里出现反直觉结果,本质是道路速度属性的赋值问题:

    • ox.add_edge_speeds()默认根据道路类型(如主干道、支路)分配预设速度,而非OSM数据中的实际限速。如果path_OX_L经过的道路被赋予的默认速度不低于path_OX_T的道路,那么更短的路径自然耗时更少。
    • travel_time由length / speed计算得出,若短路径的道路等级更高(默认速度更快),其总耗时会比更长但速度慢的路径更短,这就导致path_OX_L的时间优于path_OX_T。
  3. 验证与优化建议:

    • 对比两条路径的道路速度差异,确认速度赋值是否合理:
      # 获取两条路径的边速度
      speeds_L = ox.utils_graph.get_route_edge_attributes(graph_city, path_OX_L, 'speed_kph')
      speeds_T = ox.utils_graph.get_route_edge_attributes(graph_city, path_OX_T, 'speed_kph')
      print(f"path_OX_L平均速度: {sum(speeds_L)/len(speeds_L):.1f} km/h")
      print(f"path_OX_T平均速度: {sum(speeds_T)/len(speeds_T):.1f} km/h")
      
    • 若需要更精准的旅行时间,建议使用包含实际限速的OSM数据,或手动修正道路的speed_kph属性后再计算最短路径。

内容的提问来源于stack exchange,提问作者AliStonks

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.21 14:45:00