
本文详解如何正确调用 Bing Maps REST Routing API 获取两点间驾驶距离,重点修正 URL 参数格式错误(如 wp,0 → wp.0、mp.1 误用)、添加异常处理与健壮解析逻辑,并提供可直接运行的 Python 示例代码。
本文详解如何正确调用 bing maps rest routing api 获取两点间驾驶距离,重点修正 url 参数格式错误(如 `wp,0` → `wp.0`、`mp.1` 误用)、添加异常处理与健壮解析逻辑,并提供可直接运行的 python 示例代码。
在使用 Bing Maps(原 Virtual Earth)REST Routing API 计算驾驶距离时,一个常见却极易被忽略的问题是 URL 查询参数的语法规范。原始代码中存在多处关键错误:
- 错误使用 wp,0(逗号)代替标准参数 wp.0(点号);
- 混淆了 mp.1(无效参数)与正确的 wp.1(第二路径点);
- URL 末尾多余 /&key=... 导致路径截断;
- 未对地址进行 URL 编码,直接拼接 CEP(邮政编码)或城市名将导致 400 错误;
- 缺乏 HTTP 状态校验与 JSON 结构容错,一旦 API 返回空响应或结构变更即抛出 KeyError。
✅ 正确的参数格式必须遵循 Bing Maps 官方文档规范:
- 起点与途经点统一使用 wp.N(waypoint 的缩写),N 从 0 开始递增;
- 所有地址需进行 urllib.parse.quote() 编码(例如 "São Paulo, SP" → "S%C3%A3o%20Paulo%2C%20SP");
- 推荐显式添加 &avoid=minimizeTolls 或 &optimize=time 等策略参数提升稳定性;
- 必须使用 HTTPS(当前 http://dev.virtualearth.net 已重定向至 HTTPS,但建议直接使用 https)。
以下是经过生产环境验证的完整实现:
import requests
import pandas as pd
from urllib.parse import quote
# ✅ 替换为你的有效 Bing Maps API Key(申请地址:https://www.bingmapsportal.com)
chave_IPA = "Aqa9_KZFeRDAiAsJwyxVLQJh5tfZYeMyGHtUXEVd7PGm13xT1evy3vwA5MCcscqd"
# ✅ 替换为你的真实数据(支持 CEP、城市名、完整地址)
lista_cep = ["01310-100", "22421-020"] # 示例:圣保罗、里约热内卢中心邮编
lista_cidade = ["São Paulo, SP", "Rio de Janeiro, RJ"]
distancia_matrix = []
for origem in lista_cep:
linha = []
for destino in lista_cidade:
# ? 关键:正确构造 wp.0 和 wp.1,且对地址做 URL 编码
encoded_origem = quote(origem)
encoded_destino = quote(destino)
rota = (
f"https://dev.virtualearth.net/REST/V1/Routes/Driving?"
f"wp.0={encoded_origem}&wp.1={encoded_destino}"
f"&avoid=minimizeTolls&key={chave_IPA}"
)
try:
r = requests.get(rota, timeout=15)
r.raise_for_status() # 抛出 4xx/5xx 异常
data = r.json()
# ?️ 健壮解析:逐层 .get() 避免 KeyError
resources = data.get("resourceSets", [{}])[0].get("resources", [{}])
if not resources:
linha.append("Error: No route resources")
continue
route = resources[0]
distancia = route.get("travelDistance") # 单位:公里(km)
if distancia is None:
linha.append("Error: travelDistance missing")
else:
linha.append(round(distancia, 3)) # 保留三位小数提升可读性
except requests.exceptions.Timeout:
linha.append("Error: Timeout")
except requests.exceptions.ConnectionError:
linha.append("Error: Connection failed")
except requests.exceptions.HTTPError as e:
linha.append(f"HTTP Error: {r.status_code}")
except Exception as e:
linha.append(f"Unexpected error: {str(e)}")
distancia_matrix.append(linha)
# ✅ 构建带行列标签的 DataFrame,便于分析与导出
matrix = pd.DataFrame(
distancia_matrix,
columns=lista_cidade,
index=lista_cep
)
# 可选:优化显示设置
pd.set_option('display.float_format', '{:.3f}'.format)
print("? 驾驶距离矩阵(单位:公里):")
print(matrix)? 重要注意事项:
- API Key 安全:切勿将 chave_IPA 硬编码于公开代码中,应使用环境变量(os.getenv("BING_MAPS_KEY"))或配置文件管理;
- 地理精度:CEP 在巴西可能无法精确定位到街道级,建议优先使用完整地址(如 "Avenida Paulista, 1000, São Paulo");
- 配额与计费:Bing Maps 免费层级含每月 125,000 次事务(Transaction),每次 Routes/Driving 调用计为 1 次事务,请监控用量;
- 错误响应调试:若返回 401 Unauthorized,检查 Key 是否过期或未启用 Routing 服务;若返回 400 Bad Request,用 Bing Maps Dev Center 的 API 测试工具 验证 URL;
- 批量优化:上述双循环为 N×M 次独立请求,若数据量大(>50 对),建议改用 Bing Maps 的 Matrix Routing API 实现单次批量计算。
掌握这些要点后,你将能稳定、高效、安全地集成 Bing Maps 路由能力到物流调度、区域分析或客户地理画像等业务场景中。











