百度地图开放平台轻量路径规划

百度地图开放平台轻量路径规划

背景

由于要做等时圈研究,手头上有一些poi数据,如小区地理位置信息,地铁站点的地理位置信息,想通过等时圈把两者连接起来,如不同站点的关于小区的等时圈,这就需要时间数据,多方对比发现百度地图开放平台的轻量路径规划能够很好解决这个问题。

思路

在这里插入图片描述
比如要给图中绿色三角形找一些等时圈,直接构造等时圈太空洞,于是想在其周边一定范围内找一些poi散点,这样中心点到散点的时间和距离就能够通过轻量级路线规划找出来,有了周边所有散点之后就可以通过arcgis等值线圈起来。
轻量级路线规划服务(又名DirectionLite API )是一套REST风格的Web服务API,以HTTP/HTTPS形式提供了路线规划服务。由于我们主要研究对象时上班族,所以选择公交路线(含地铁)规划教适宜,公交路线规划时根据起讫(qi)点坐标规划同城公共交通出行路线和耗时,支持公交、地铁出行方式,这里的起店为地铁站,讫点所有小区。上海有415个地铁站,15000+小区,要把所有路线算出来,至少有600万条数据,数据量如此之大,完全实现不太实际,这里只选择特殊的起点来计算其到其他所有终点的距离和时间。效果大致如下
在这里插入图片描述

完整代码

import requests #导入服务器请求模块
import pandas as pd #导入数据分析模块
import pymysql
metro_data=pd.read_excel("D:\Python项目\轻量级路线规划\上海地铁站.xlsx",index_col="序号")
community_data=pd.read_excel("D:\Python项目\轻量级路线规划\个人挂牌.xlsx",index_col="序号")
station=metro_data["站名"]
community=community_data["小区名称"]
lng_community=community_data["经度"]
lat_community=community_data["纬度"]
lng_lat_metro=metro_data["站点经纬度"]
lng_lat_community=community_data["小区经纬度"]

db=pymysql.connect("localhost","root","123456","OD",charset="utf8") #连接数据库
cursor=db.cursor() #创建游标

cursor.execute("drop table if exists time_distance") #以重写的方式写入
c_sql="""create table time_distance(
    origin_name varchar(10), 
    destination_name varchar(20),
    destination_lng varchar(50), 
    destination_lat varchar(20),
    distance varchar(10), 
    time_cosuming varchar(40) 
     )ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=UTF8MB4"""
cursor.execute(c_sql) #执行创建表操作
                
def routing(): #定义根据起讫点计算路径的距离和时间并写入csv
    for origin_index,origin_point in enumerate(lng_lat_metro[41:42]):   #起点循环 
        for destination_index,destination_point in enumerate(lng_lat_community): #终点循环
            url="http://api.map.baidu.com/directionlite/v1/transit?origin="+origin_point+"&destination="+destination_point+"&ak=您的AK"  #GET请求
            header={'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.77 Safari/537.36'} #构造请求头
            response=requests.get(url,headers=header) #发出请求
            answer=response.json() #json化
            if answer["status"]==0: #如果成功返回
                #print(len(answer["result"]["routes"])) #总共出行方案
                origin_name=station[41] #起始站
                destination_name=community[destination_index] #小区名称
                destination_lng=str(lng_community[destination_index]) #终点经度
                destination_lat=str(lat_community[destination_index]) #终点纬度
                distance=str(round(answer["result"]["routes"][0]["distance"]/1000,1)) #距离,转化为千米
                time_cosuming=str(round(answer["result"]["routes"][0]["duration"]/60,1)) #时长,转化为分钟 
                print(origin_name,destination_name,destination_lng,destination_lat,distance,time_cosuming) #测试
                insert_data=("insert into time_distance(origin_name,destination_name,destination_lng,destination_lat,distance,time_cosuming)""values(%s,%s,%s,%s,%s,%s)")
                target_data=([origin_name,destination_name,destination_lng,destination_lat,distance,time_cosuming])
                cursor.execute(insert_data,target_data) #执行插入操作
                db.commit()
                
if __name__=="__main__":
    routing()

代码解读

首先把地铁经纬度读取进来,把小区经纬度读取进来,然后构造请求url,起点的经纬度数据为地铁站的,讫点的经纬度数据为小区的,构造好起讫点请求url,就明确了从哪里到哪里,接下来就是怎么走的问题,紧接着用requests向服务器发出请求,返回json格式数据,获取相应的字段如时间和距离等,然后把起点名,终点名和终点的经度,终点的纬度整理成一条记录最后存入MySQL数据库里,便得到地铁站到所有小区的时间和距离数据,接下来就是利用arcgis软件将这些数据可视化的工作。

改进

1,直接写入csv
写入MySQL数据库然后再导出,显得麻烦了,直接写入csv或许更便捷些,下面代码是直接写入csv里面的,请注意写入数据和获取返回数据的逻辑,应该先建立一个csv空文件,然后立即写入表头,再requests循环请求,最后才是一条一条返回数据的写入
2,增加程序的泛化能力
上面程序显然是针对特定的起点和讫点,不单单对地铁站和小区,改成一般化的起讫点。

import csv #导入csv模块
import requests #导入服务器请求模块
import pandas as pd #导入数据分析模块
origin_data=pd.read_excel("起点.xlsx")
destination_data=pd.read_excel("讫点.xlsx")
origin_place=origin_data["起点"] #起点名
destination_place=destination_data["讫点"] #讫点名
lng_lat_origin=origin_data["起点经纬度"]
lng_lat_destination=destination_data["讫点经纬度"]              
def routing(): #定义根据起讫点计算路径的距离和时间并写入csv
    path="等时圈.csv" #当前路径下新建一个等时圈csv文件
    with open(path,"w+",newline='') as csv_file: #打开文件,追加
        writer=csv.writer(csv_file) 
        header=["起点","终点","终点经度","终点纬度","距离(m)","时间(min)"] #构造表头
        writer.writerow(header) #先写入表头  
        for origin_index,origin_point in enumerate(lng_lat_origin[0:1]):   #起点循环 
            for destination_index,destination_point in enumerate(lng_lat_destination): #终点循环
                #print(origin_point,destination_point) #测试起讫点经纬度
                url="http://api.map.baidu.com/directionlite/v1/walking?origin="+origin_point+"&destination="+destination_point+"&ak=你的AK"  #GET请求
                header={'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.77 Safari/537.36'} #构造请求头
                response=requests.get(url,headers=header) #发出请求
                answer=response.json() #json化
                if answer["status"]==0: #如果成功返回
                    #print(len(answer["result"]["routes"])) #总共出行方案
                    origin_name=str(origin_place[origin_index]) #起始点
                    destination_name=destination_place[destination_index] #讫点名称
                    destination_lng=str(lng_lat_destination[destination_index]).split(",")[1] #终点经度
                    destination_lat=str(lng_lat_destination[destination_index]).split(",")[0] #终点纬度
                    distance=str(round(answer["result"]["routes"][0]["distance"],0)) #距离,转化为千米
                    time_cosuming=str(round(answer["result"]["routes"][0]["duration"]/60,0)) #时长,转化为分钟 
                    data_row=[origin_name,destination_name,destination_lng,destination_lat,distance,time_cosuming]
                    print(data_row) #测试
                    writer.writerow(data_row) #写入csv
        csv_file.close() #全部写入后关闭csv文件
if __name__=="__main__":
    routing()           

总结

(1)轻量路径规划帮助文档
(2)个人认证的用户ak配额只有30000条,注意不要超过配额了
(3)经纬度记得处理成6位小数
(4)对于数据量不大的可以存为csv,没必要存到数据库里面

发布了45 篇原创文章 · 获赞 12 · 访问量 8642

猜你喜欢

转载自blog.csdn.net/zengbowengood/article/details/103860624