up之前无意了解到百度地图开放平台:链接
有一些接口是免费提供的(需要用自己的账号去领取),然后我就萌生了一个想法,我想用这些接口调用到的数据去做一些数据分析与可视化。
这个项目目前还不够完善,只有一些基础的功能和简单的展示,在可视化上并没有特别鲜明和优秀的体现。
项目地址:点击跳转至gitee
话不多说,直接看项目
代码:
项目框架:
核心代码部分:
1.调用百度地图开发平台中第一个接口(这里称为接口a),其功能是实现地名转换成经纬度。
from urllib.request import urlopen
from urllib.parse import quote
import json
def get_coordinate(adress): #传入一个地名列表
coordinate_list = []
for i in adress:
url = 'https://api.map.baidu.com/geocoding/v3/?address='
output = 'json'
ak = 'ak'
add = quote(i) #使用quote进行编码 为了防止中文乱码
url2 = url + add + '&output=' + output + '&ak=' + ak
req = urlopen(url2)
res = req.read().decode()
temp = json.loads(res)
coordinate = [i,round(temp['result']['location']['lng'],10),round(temp['result']['location']['lat'],10)]#仅仅保留10位小数
# coordinate = [temp['result']['location']['lng'], temp['result']['location']['lat']] #默认14位小数
coordinate_list.append(coordinate)
return coordinate_list
其中的ak是在百度地图开发平台创建完你自己的应用之后会得到的一串数字,你更换成自己的就行了。
返回实例:
2.调用第二个接口(这里称为接口b),该接口的功能是:提供经纬度,它会返回该经纬度下附近的道路的拥堵状况。
import time
import pandas as pd
import requests
from Scripts.api_to_get_coordinate import pachong_get_coordinate
url = 'https://api.map.baidu.com/traffic/v1/bound'
headers = {
"User-Agent": 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/106.0.0.0 Safari/537.36 Edg/106.0.1370.52'
}
x = []
name_list = ["广州市五山街道","广州市元岗街道","广州市兴华街道","广州市冼村街道",
"广州市凤凰街道","广州市前进街道","广州市员村街道","广州市天园街道",
"广州市天河南街道","广州市新塘街道","广州市林和街道","广州市棠下街道",
"广州市沙东街道"]
coordinate_list = pachong_get_coordinate.get_coordinate(name_list) #传入一个地名列表
for n,i in enumerate(coordinate_list):
baselng = i[1]
baselat = i[2]
# widelng = 0.012
# widelat = 0.012
widelng = 0.012
widelat = 0.012
startlat = round(baselat + widelat, 10)
endlat = round(startlat + widelat, 10)
startlng = round(baselng + widelng, 10)
endlng = round(startlng + widelng, 10)
locStr = str(startlat) + "," + str(startlng) + ";" + str(endlat) + "," + str(endlng)
params = {
"bounds": locStr,
"road_grade": 0,
# "ak": AkDict[AkNum]
"ak":'ak'
}
res = requests.get(url=url, params=params, headers=headers, timeout=(3, 7)) #一个免费账号一天至多调用两千次
data = res.json()
if data.get('road_traffic') is not None:
for k in range(0, len(data.get('road_traffic'))):
road_traffic = data.get('road_traffic')
evaluation = data.get('evaluation')
road_name = road_traffic[k].get('road_name')
status = evaluation.get('status')
if (data.get('road_traffic')[k]).get("congestion_sections") is not None:
congestion_sections = (road_traffic[k]).get('congestion_sections')
status = (congestion_sections[0]).get('status')
speed = (congestion_sections[0]).get('speed')
congestion_distance = (congestion_sections[0]).get('congestion_distance')
congestion_trend = (congestion_sections[0]).get('congestion_distance')
section_desc = (congestion_sections[0]).get('section_desc') #这里是需要的数据,要哪些就保留那些
else:
speed = congestion_distance = congestion_trend = section_desc = ''
x.append([road_name, status, speed, congestion_distance, congestion_trend, section_desc, startlat, startlng])
print(data)
time.sleep(2)
df = pd.DataFrame(x)
df.to_csv('../../output/output_csv/%s.csv'%(name_list[n]))
返回示例:
现在我们有了这个功能之后,就可以相应的扩大我们的区域范围,我们可以把范围扩大到整个区甚至是整个广州市。我们可以利用这些数据,根据我们想要的内容,将有用的信息写入到csv文件中,整合并且处理之后可以用于绘图。
3.绘图
from pyecharts.charts import Bar, Grid, Line, Pie, Tab, Timeline
from pyecharts.globals import ThemeType
import csv
from pyecharts import options as opts
with open("../../output/output_csv/old_all_road.csv", "r", encoding='utf-8') as csvfile:
reader = csv.reader(csvfile)
data = []
road_name = []
for line in reader:
if line[1] != 'UNKNOW':
data.append([line[1], int(line[2])])
data = data[1:]
data = sorted(data, key=lambda x: x[1], reverse=True)
data = data[:11]
name_list = []
count_list = []
for i in data:
if i[1] > 1:
name_list.append(i[0])
count_list.append(i[1])
def road_charts(count_list,name_list):
c = (
Bar(init_opts=opts.InitOpts(theme=ThemeType.LIGHT,width="1400px", height="600px"))
.add_xaxis(name_list)
.add_yaxis("当前区域排名靠前的拥堵路段",count_list, category_gap="50%")
.set_series_opts(
label_opts=opts.LabelOpts(
position="right"
)
).set_global_opts(
brush_opts=opts.BrushOpts(), # 设置操作图表的画笔功能
toolbox_opts=opts.ToolboxOpts(), # 设置操作图表的工具箱功能
yaxis_opts=opts.AxisOpts(axislabel_opts=opts.LabelOpts(formatter="{value} 量级"),name="拥堵程度"), # 设置Y轴名称、定制化刻度单位
xaxis_opts=opts.AxisOpts(name="道路名称"), # 设置X轴名称
)
)
return c
def road_pie2_charts(count_list,name_list):
flag1,flag2,flag3,flag4 = 0,0,0,0
name1,name2,name3,name4 = "","","",""
for i in range(len(count_list)):
if count_list[i]==1:
flag1 +=1
name1 = name1 +","+ name_list[i]
elif count_list[i]==2:
flag2 +=1
name2 = name2 +","+ name_list[i]
elif count_list[i]==3:
flag3 +=1
name3 = name3 +","+ name_list[i]
elif count_list[i]==4:
flag4 +=1
name4 = name4 +","+ name_list[i]
pie2_count_list = [flag1,flag2,flag3,flag4]
pie2_name_list = [name1.lstrip(',')+"(通畅)",name2.lstrip(',')+"(轻度拥堵)",name3.lstrip(',')+"(中度拥堵)",name4.lstrip(',')+"(重度拥堵)"]
pie2 = (
Pie()
.add("", [list(z) for z in zip(pie2_name_list,pie2_count_list)])
.set_colors(["blue", "green", "pink", "red", "orange", "yellow","purple"])
.set_series_opts(label_opts=opts.LabelOpts(formatter="{b}: {c}"))
)
return pie2
def road_pie1_charts(count_list,name_list):
pie1 = (
Pie()
.add("", [list(z) for z in zip(name_list,count_list)])
.set_colors(["blue", "green", "pink", "red", "orange", "yellow","purple"])
.set_series_opts(label_opts=opts.LabelOpts(formatter="{b}: {c}"))
)
return pie1
tab = Tab()
tab.add(road_charts(count_list,name_list), "当前时段排名前十的拥堵路段(柱状图)")
tab.add(road_pie1_charts(count_list,name_list), "当前时段排名前十的拥堵路段(饼图)")
tab.add(road_pie2_charts(count_list,name_list), "当前时段排名前十的拥堵路段(饼图)")
tab.render("../../output/output_html/graphs.html")
tab.render_notebook()
绘图展示:
上述三张图都是展现了某个时段下,整个广州市中较为拥堵的几个路段。由于时间原因,我还没有想到用什么图形去表现我们整个交通状况会更加直观,所以就暂时使用了直方图和饼图,如果各位有更好的想法,直接用我们接口爬到的数据去绘图即可。
总结:
总的来讲这个项目是比较简单的,大家也可以通过本次项目学会如何调用接口。最近百度地图好像推出了百度地图慧眼这个项目:点击跳转至百度地图慧眼 里面有很多各式各样的接口,我们可以充分地去利用这些接口,获取一些数据,然后再实现我们自己想要的数据分析与可视化项目。
补充:
如有其他问题,请私信我,谢谢。