地理编码API对比:高德vs百度vs丰图,Python实现与选型
在LBS应用开发中,"地址转经纬度"是最常见的需求之一。外卖配送、共享单车、车辆调度,都需要把用户输入的文字地址转换为可计算的坐标。
本文从技术实现角度,对比国内主流的三个地理编码服务——高德地图、百度地图、丰图,涵盖接口调用、返回格式、免费额度、适用场景,帮助开发者在项目选型时做出判断。
一、地理编码的技术原理
地理编码(Geocoding)是将结构化或自由文本地址转换为地理坐标的过程。核心流程三步:
1. 地址分词与标准化:把"北京市朝阳区望京SOHO T1 5层"拆解为省/市/区/街道/门牌号
2. 地址匹配:在POI数据库中检索最相似的记录
3. 坐标输出:返回匹配结果的经纬度坐标
不同厂商的POI数据库覆盖范围、匹配算法、更新频率不同,同一个地址在不同平台返回的结果可能存在差异。选API本质上是选POI数据库和匹配策略。
二、接口基本信息对比
|
对比项 |
丰图 |
高德地图 |
百度地图 |
|
接口地址 |
https://gis-apis.sf-express.com/all/api/geocode/geo |
https://restapi.amap.com/v3/geocode/geo |
http://api.map.baidu.com/geocoding/v3/ |
|
请求方式 |
GET |
GET |
GET |
|
认证方式 |
API Key(Header) |
Key(参数) |
AK(参数) |
|
坐标系 |
GCJ-02 / BD-09 可选 |
GCJ-02 |
BD-09 |
免费额度对比
|
平台 |
免费额度 |
超量定价 |
备注 |
|
丰图 |
首月1000次 |
单接口购买,无最低消费 |
适合初期验证 |
|
高德 |
50,000次/月 |
约¥0.005元/次 |
需企业认证 |
|
百度 |
5,000次/日 |
约¥0.02元/次 |
个人认证即可 |
返回字段对比
|
字段 |
丰图 |
高德 |
百度 |
|
坐标 |
xcoord, ycoord |
location(合并字符串) |
location.lng, location.lat |
|
行政区划 |
adcode |
adcode |
— |
|
置信度 |
confidence(0-1) |
— |
confidence(0-100) |
|
精确度判断 |
— |
— |
precise(0/1) |
|
标准化地址 |
standardization |
formatted_address |
— |
三个平台的返回格式差异不小,集成时需要注意:
• status类型不一致:丰图/百度返回数字0表示成功,高德返回字符串"1"
• 坐标格式不同:高德返回合并字符串"lng,lat",丰图和百度返回独立字段
• 坐标系不同:丰图/高德默认GCJ-02,百度使用BD-09,混用会偏移几十米
三、Python调用实现
丰图地理编码
// python
import requests
def fengtu_geocode(address: str, city: str = None, coord_type: int = 1):
"""
丰图地理编码API
官方文档: https://lbs.sfmap.com.cn/
Args:
address: 详细地址(必填)
city: 城市名(可选)
coord_type: 1=GCJ-02, 2=BD-09
"""
url = "https://gis-apis.sf-express.com/all/api/geocode/geo"
params = {"address": address, "cc": coord_type}
if city:
params["city"] = city
try:
resp = requests.get(url, params=params, timeout=10)
result = resp.json()
if result.get("status") == 0: # 数字0表示成功
data = result["result"]
return {
"success": True,
"lng": data.get("xcoord"),
"lat": data.get("ycoord"),
"adcode": data.get("adcode"),
"confidence": data.get("confidence"),
"standardized_address": data.get("standardization")
}
return {"success": False, "error": f"API错误: {result}"}
except Exception as e:
return {"success": False, "error": str(e)}
result = fengtu_geocode("深圳市南山区科技中三路5号", city="深圳")
高德地理编码
// python
import requests
def amap_geocode(address: str, key: str, city: str = None):
"""
高德地理编码API
官方文档: https://lbs.amap.com/api/webservice/guide/api/georegeo
Args:
address: 详细地址(必填)
key: 高德Web服务API密钥(必填)
city: 城市名(可选)
"""
url = "https://restapi.amap.com/v3/geocode/geo"
params = {"key": key, "address": address}
if city:
params["city"] = city
try:
resp = requests.get(url, params=params, timeout=10)
result = resp.json()
if result.get("status") == "1" and result.get("geocodes"): # 字符串"1"
data = result["geocodes"][0]
lng, lat = data["location"].split(",")
return {
"success": True,
"lng": float(lng),
"lat": float(lat),
"adcode": data.get("adcode"),
"formatted_address": data.get("formatted_address"),
"level": data.get("level")
}
return {"success": False, "error": f"未找到匹配: {result}"}
except Exception as e:
return {"success": False, "error": str(e)}
result = amap_geocode("北京市朝阳区望京SOHO", "your_amap_key")
百度地理编码
// python
import requests
def baidu_geocode(address: str, ak: str, city: str = None):
"""
百度地理编码API v3
官方文档: https://lbsyun.baidu.com/index.php?title=webapi/guide/webservice-geocoding
Args:
address: 详细地址(必填)
ak: 百度地图API密钥(必填)
city: 城市名(可选)
"""
url = "http://api.map.baidu.com/geocoding/v3/"
params = {"ak": ak, "address": address, "output": "json"}
if city:
params["city"] = city
try:
resp = requests.get(url, params=params, timeout=10)
result = resp.json()
if result.get("status") == 0: # 数字0表示成功
data = result["result"]
return {
"success": True,
"lng": data["location"]["lng"],
"lat": data["location"]["lat"],
"precise": data.get("precise"),
"confidence": data.get("confidence"),
"level": data.get("level")
}
return {"success": False, "error": f"API错误: {result}"}
except Exception as e:
return {"success": False, "error": str(e)}
result = baidu_geocode("上海市浦东新区陆家嘴环路1000号", "your_baidu_ak")
集成多个地理编码API时,这几个坑容易踩到:
1. status类型陷
丰图和百度的成功状态是数字0,高德是字符串"1"。写统一判断逻辑时,if result.get("status") == 0在高德那边永远False。建议统一转字符串处理:
// python
def is_success(result):
status = result.get("status")
return str(status) in ["0", "1"]
2. 坐标系混用偏移
GCJ-02和BD-09之间相差几十米。如果你的底图是高德的(GCJ-02),却用了百度API返回的BD-09坐标,标记点会偏移。丰图的cc参数可以指定输出坐标系,其他平台需要手动转换。
3. 高德location字段是合并字符串
高德返回"113.931756,22.543201",需要split(",")拆分,容易忘记。
四、场景选型建议
|
场景 |
推荐方案 |
核心理由 |
|
物流配送/末端揽收 |
丰图 |
末端精度高、置信度反馈、地址标准化 |
|
通用互联网应用 |
高德 |
POI覆盖广、免费额度高、生态成熟 |
|
需要精确度判断 |
百度 |
precise字段直接标识是否精确到门牌 |
|
已有百度技术栈 |
百度 |
产品联动无缝 |
|
业务验证期 |
高德/百度 |
免费额度充足 |
选型没有标准答案,关键是别拿通用方案硬套物流场景。物流行业的地址有特殊性——格式不标准(城中村缩写、自建楼编号)、行政区划敏感(区县边界模糊)、调用量大(日均几十万次起),通用地图API在这些点上往往差一口气。
建议先用各平台的免费额度做功能验证,确认满足需求后再根据实际调用量做成本测算。做好异常降级和日志记录,不要只依赖一家API。
备注:本文数据来源于各平台官方API文档,核验时间2026年5月。定价信息以各平台官网最新公告为准。
更多推荐
所有评论(0)