如何使用 arcGIS api 获取两个地址之间的多次行驶时间

How to get multiple drive time between two addresses using arcGIS api

我正在使用 ArcGIS api (ArcMap - 10.5.1),我正在尝试获取两个地址之间的行驶时间。我可以获得两点之间的行驶时间,但我不知道如何遍历多个点。我有一百个地址。我不断收到

AttributeError: 'NoneType' object has no attribute '_tools'

这是我正在使用的 Pandas 数据框。我有两列索引。第一列是原始地址,第二列是第二个地址。如果可能的话,我很乐意用开车时间重新排成一行。

df2
          Address_1                                        Address_2
0  1600 Pennsylvania Ave NW, Washington, DC 20500    2 15th St NW, Washington
1  400 Broad St, Seattle, WA 98109                   325 5th Ave N, Seattle

这是我从中获取代码的 link https://developers.arcgis.com/python/guide/performing-route-analyses/

我尝试破解这段代码。具体如下代码。

def pairwise(iterable):
    a, b = tee(iterable)
    next(b, None)
    return zip(a, b)

#empty list - will be used to store calculated distances
list = [0]

# Loop through each row in the data frame using pairwise
for (i1, row1), (i2, row2) in pairwise(df.iterrows()):

https://medium.com/how-to-use-google-distance-matrix-api-in-python/how-to-use-google-distance-matrix-api-in-python-ef9cd895303c

我查了一下 non_type 是什么意思,所以我试着打印出来看看是否有任何东西可以打印出来并且它工作正常。我主要使用 R,不常使用 python。

for (i,j) in pairwise(df2.iterrows()):
    print(i)
    print(j)
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt 
from copy import deepcopy
from datetime import datetime
from IPython.display import HTML
import json
from arcgis.gis import GIS
import arcgis.network as network
import arcgis.geocoding as geocoding
from itertools import tee



user_name = 'username'
password = 'password'
my_gis = GIS('https://www.arcgis.com', user_name, password)

route_service_url = my_gis.properties.helperServices.route.url
route_service = network.RouteLayer(route_service_url, gis=my_gis)

for (i,j) in pairwise(df2.iterrows()):
    stop1_geocoded = geocoding.geocode(i)
    stop2_geocoded = geocoding.geocode(j)

    stops = '{0},{1}; {2},{3}'.format(stop1_geocoded[0]['attributes']['X'],
                                      stop1_geocoded[0]['attributes']['Y'],
                                      stop2_geocoded[0]['attributes']['X'],
                                      stop2_geocoded[0]['attributes']['Y'])
    route_layer = network.RouteLayer(route_service_url, gis=my_gis)
    result = route_layer.solve(stops=stops, return_directions=False, return_routes=True, 
                               output_lines='esriNAOutputLineNone', return_barriers=False, 
                               return_polygon_barriers=False, return_polyline_barriers=False)
    travel_time = result['routes']['features'][0]['attributes']['Total_TravelTime']

    print("Total travel time is {0:.2f} min".format(travel_time))

预期的输出是一个驱动时间列表。我尝试将所有内容附加到数据框,那将是理想的。所以理想的输出应该是 3 列——地址 1、地址 2 和行驶时间。该代码一次处理一个地址(而不是 i,j 它只是两个地址作为字符串,没有 for 语句)。

示例:

          Address_1                                        Address_2
0  1600 Pennsylvania Ave NW, Washington, DC 20500    2 15th St NW, Washington
1  400 Broad St, Seattle, WA 98109                   325 5th Ave N, Seattle

         drive_time
0  7 minutes
1  3 minutes

您没有必要使用成对函数。只需将 arcGIS 代码包装在一个函数中,该函数将为您提供 return 时间,这样您就可以将值映射为数据框上的新列。

还要确保导入时间库,arcGIS 文档中没有注明,但 运行 此操作需要。

`

def getTime(row):    

    try:
        stop1_geocoded = geocoding.geocode(row.df_column_1)
        stop2_geocoded = geocoding.geocode(row.df_column_2)

        stops = '{0},{1}; {2},{3}'.format(stop1_geocoded[0]['attributes']['X'],
                                          stop1_geocoded[0]['attributes']['Y'],
                                          stop2_geocoded[0]['attributes']['X'],
                                          stop2_geocoded[0]['attributes']['Y'])

        route_layer = network.RouteLayer(route_service_url, gis=my_gis)
        result = route_layer.solve(stops=stops, return_directions=False, return_routes=True, 
                                   output_lines='esriNAOutputLineNone', return_barriers=False, 
                                   return_polygon_barriers=False, return_polyline_barriers=False)

        travel_time = result['routes']['features'][0]['attributes']['Total_TravelTime']
        time = "Total travel time is {0:.2f} min".format(travel_time)

        return time

    except RuntimeError:
        return 

streets['travel_time'] = streets.apply(getTime, axis=1)

`