Skip to content

Network search method

Elizabeth Sall edited this page Aug 1, 2019 · 1 revision

Find all the links that have 2 lanes AND are named a variation of 6th between A and B

{
    'link':[
        {'name': ['6th','Sixth','sixth']},
        {'lanes': [2]},
        ],
     'A':{'osmnodeid': '187899923'},
     'B':{'osmnodeid': '187865924'},
}

Pseudocode

A_id = selection['A']['osmnodeid']
B_id = selection['B']['osmnodeid']

# find candidate links and nodes which satisfy link['name']
candidate_links = links[ links['name'] in selection['link']['name'] ]
node_list_osmnodeids = list(set(candidate_links['u'].aslist ,candidate_links['v'].aslist ))

def add_breadth(candidate_links, nodes=nodes_gdf, links = links_gdf):
   #add outbound and inbound reference IDs from existing nodes
   node_list_osmnodeids = list(set(candidate_links['u'].aslist ,candidate_links['v'].aslist ))
   candidate_nodes = nodes[ nodes['osmnodeid'] in node_list_osmnodeids ]
   links_refs_to_add = list(set(candidate_nodes['outboundReferenceId']+candidate_nodes['inboundReferenceId']))
   links_to_add = links[ links['refs'] in links_refs_to_add ]
   return candidate_links.concatenate(links_to_add)

# Add breadth to graph until have at least A and B
i = 0
MAX_BREADTH = 2
while A_id not in node_list_osmnodeids or B_id not in node_list_osmnodeids and i<MAX_BREADTH:
   candidate_links = add_breadth(candidate_links)
   node_list_osmnodeids = list(set(candidate_links['u'].aslist ,candidate_links['v'].aslist ))
   i += 1

# Complain if it doesn't give back something useful
if A_id not in node_list_osmnodeids or B_id not in node_list_osmnodeids:
   raise.SpecificityError("search terms not specific enough")
   sys.exit(2)

# Try and do a shortest path, using name as the largest weight
candidate_nodes = nodes[ nodes['osmnodeid'] in node_list_osmnodeids ]

# add weight to favor links with the name
# can't remember if this should be large or small to favor :-)
candidate_links['weight'] = 10*links[ links['name'] in selection['link']['name'] ]  
 
import osmnx as ox
G  = ox.gdfs_to_graph(candidate_nodes, candidate_links)

# should return a list of nodes in the path
sp_list = nx.shortest_path(G,A_id,B_id,weight = 'weight') 

# select links in the shortest path that satisfy the criteria
sp_links = candidate_links[candidate_links['u'] in sp_list and candidate_links['v'] in sp_list]
select_links = sp_links
for variable, requirement in selection['link'].items():
  select_links = select_links[ select_links[variable] in requirement ] #should be able to do a 'like' match or partial match


Find all the links that are a motorway between A and B

{
    'link':[
        {'facility_type': ['motorway']},
        ],
     'A':{'osmnodeid': '187899923'},
     'B':{'osmnodeid': '187865924'},
}

Related:

Clone this wiki locally