Skip to content

Commit

Permalink
[FEAT] Changed id type to Union{Int, String}
Browse files Browse the repository at this point in the history
  • Loading branch information
ltokareva committed Mar 13, 2024
1 parent c5a0b8f commit 18e73d4
Show file tree
Hide file tree
Showing 19 changed files with 394 additions and 227 deletions.
3 changes: 2 additions & 1 deletion Project.toml
Original file line number Diff line number Diff line change
@@ -1,13 +1,14 @@
name = "LightOSM"
uuid = "d1922b25-af4e-4ba3-84af-fe9bea896051"
authors = ["Jack Chan <[email protected]>"]
version = "0.2.12"
version = "0.3.0"

[deps]
DataStructures = "864edb3b-99cc-5e75-8d2d-829cb0a9cfe8"
Graphs = "86223c79-3864-5bf0-83f7-82e725a168b6"
HTTP = "cd3eb016-35fb-5094-929b-558a96fad6f3"
JSON = "682c06a0-de6a-54ab-a142-c8b1cf79cde6"
JSON3 = "0f8b85d8-7281-11e9-16c2-39a750bddbf1"
LightXML = "9c8b4983-aa76-5018-a973-4c85ecc9e179"
MetaGraphs = "626554b9-1ddb-594c-aa3c-2596fe9399a5"
NearestNeighbors = "b8a86587-4115-5ab1-83bc-aa920d37bbce"
Expand Down
2 changes: 1 addition & 1 deletion src/constants.jl
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
"""
Default data types used to construct OSMGraph object.
"""
const DEFAULT_OSM_ID_TYPE = Int64
const DEFAULT_OSM_INDEX_TYPE = Int32
const DEFAULT_OSM_ID_TYPE = Union{Integer, String}
const DEFAULT_OSM_EDGE_WEIGHT_TYPE = Float64
const DEFAULT_OSM_MAXSPEED_TYPE = Int16
const DEFAULT_OSM_LANES_TYPE = Int8
Expand Down
26 changes: 13 additions & 13 deletions src/graph.jl
Original file line number Diff line number Diff line change
Expand Up @@ -199,11 +199,11 @@ end


"""
add_node_and_edge_mappings!(g::OSMGraph{U,T,W}) where {U <: Integer,T <: Integer,W <: Real}
add_node_and_edge_mappings!(g::OSMGraph{U,T,W}) where {U <: Integer,T <: DEFAULT_OSM_ID_TYPE,W <: Real}
Adds mappings between nodes, edges and ways to `OSMGraph`.
"""
function add_node_and_edge_mappings!(g::OSMGraph{U,T,W}) where {U <: Integer,T <: Integer,W <: Real}
function add_node_and_edge_mappings!(g::OSMGraph{U,T,W}) where {U <: DEFAULT_OSM_INDEX_TYPE,T <: DEFAULT_OSM_ID_TYPE,W <: Real}
for (way_id, way) in g.ways
@inbounds for (i, node_id) in enumerate(way.nodes)
if haskey(g.node_to_way, node_id)
Expand Down Expand Up @@ -266,11 +266,11 @@ function add_node_tags!(g::OSMGraph)
end

"""
adjacent_node(g::OSMGraph, node::T, way::T)::Union{T,Vector{<:T}} where T <: Integer
adjacent_node(g::OSMGraph, node::T, way::T)::Union{T,Vector{<:T}} where T <: DEFAULT_OSM_ID_TYPE
Finds the adjacent node id on a given way.
"""
function adjacent_node(g::OSMGraph, node::T, way::T)::Union{T,Vector{<:T}} where T <: Integer
function adjacent_node(g::OSMGraph, node::T, way::T)::Union{T,Vector{<:T}} where T <: DEFAULT_OSM_ID_TYPE
way_nodes = g.ways[way].nodes
if node == way_nodes[1]
return way_nodes[2]
Expand Down Expand Up @@ -300,7 +300,7 @@ Adds restrictions linked lists to `OSMGraph`.
# Example
`[from_way_node_index, ...via_way_node_indices..., to_way_node_index]`
"""
function add_indexed_restrictions!(g::OSMGraph{U,T,W}) where {U <: Integer,T <: Integer,W <: Real}
function add_indexed_restrictions!(g::OSMGraph{U,T,W}) where {U <: DEFAULT_OSM_INDEX_TYPE,T <: DEFAULT_OSM_ID_TYPE,W <: Real}
g.indexed_restrictions = DefaultDict{U,Vector{MutableLinkedList{U}}}(Vector{MutableLinkedList{U}})

for (id, r) in g.restrictions
Expand All @@ -321,7 +321,7 @@ function add_indexed_restrictions!(g::OSMGraph{U,T,W}) where {U <: Integer,T <:
from_node = adjacent_node(g, r.via_node, r.from_way)::T
for to_way in restricted_to_ways
to_node_temp = adjacent_node(g, r.via_node, to_way)
to_node = isa(to_node_temp, Integer) ? [to_node_temp] : to_node_temp
to_node = isa(to_node_temp, DEFAULT_OSM_ID_TYPE) ? [to_node_temp] : to_node_temp

for tn in to_node
# only_straight_on restrictions may have multiple to_nodes
Expand Down Expand Up @@ -403,15 +403,15 @@ end
Adds a Graphs.AbstractGraph object to `OSMGraph`.
"""
function add_graph!(g::OSMGraph{U, T, W}, graph_type::Symbol=:static) where {U <: Integer, T <: Integer, W <: Real}
function add_graph!(g::OSMGraph{U, T, W}, graph_type::Symbol=:static) where {U <: DEFAULT_OSM_INDEX_TYPE, T <: DEFAULT_OSM_ID_TYPE, W <: Real}
if graph_type == :light
g.graph = DiGraph{T}(g.weights)
g.graph = DiGraph{U}(g.weights)
elseif graph_type == :static
g.graph = StaticDiGraph{U,U}(StaticDiGraph(DiGraph(g.weights)))
elseif graph_type == :simple_weighted
g.graph = SimpleWeightedDiGraph{U,W}(g.weights)
elseif graph_type == :meta
g.graph = MetaDiGraph(DiGraph{T}(g.weights))
g.graph = MetaDiGraph(DiGraph{U}(g.weights))
for (o, d, w) in zip(findnz(copy(transpose(g.weights)))...)
set_prop!(g.graph, o, d, :weight, w)
end
Expand Down Expand Up @@ -456,7 +456,7 @@ function trim_to_largest_connected_component!(g::OSMGraph{U, T, W}, graph, weigh
end

"""
add_dijkstra_states!(g::OSMGraph{U,T,W}) where {U <: Integer,T <: Integer,W <: Real}
add_dijkstra_states!(g::OSMGraph{U,T,W}) where {U <: Integer,T <: DEFAULT_OSM_ID_TYPE,W <: Real}
Adds precomputed dijkstra states for every source node in `OSMGraph`. Precomputing all dijkstra
states is a O(V² + ElogV) operation, where E is the number of edges and V is the number of vertices,
Expand All @@ -465,9 +465,9 @@ may not be possible for larger graphs. Not recommended for graphs with greater t
Note: Not using `cost_adjustment`, i.e. not consdering restrictions in dijkstra computation,
consider adding in the future.
"""
function add_dijkstra_states!(g::OSMGraph{U,T,W}) where {U <: Integer,T <: Integer,W <: Real}
function add_dijkstra_states!(g::OSMGraph{U,T,W}) where {U <: DEFAULT_OSM_INDEX_TYPE,T <: DEFAULT_OSM_ID_TYPE,W <: Real}
@warn "Precomputing all dijkstra states is a O(V² + ElogV) operation, may not be possible for larger graphs."
g.dijkstra_states = Vector{Vector{U}}(undef, n)
g.dijkstra_states = Vector{Vector{U}}(undef, nv(g.graph))
set_dijkstra_state!(g, collect(vertices(g.graph)))
end

Expand All @@ -480,7 +480,7 @@ Returns a 3-by-n matrix where each column is the `xyz` coordinates of a node. Co
correspond to the `g.graph` vertex indices.
"""
function get_cartesian_locations(g::OSMGraph)
node_locations = [index_to_node(g, index).location for index in 1:nv(g.graph)]
node_locations = [index_to_node(g, index).location for index in DEFAULT_OSM_INDEX_TYPE(1):DEFAULT_OSM_INDEX_TYPE(nv(g.graph))]
return to_cartesian(node_locations)
end

Expand Down
53 changes: 24 additions & 29 deletions src/graph_utilities.jl
Original file line number Diff line number Diff line change
@@ -1,30 +1,29 @@
"""
index_to_node_id(g::OSMGraph, x::Integer)
index_to_node_id(g::OSMGraph, x::Vector{<:Integer})
index_to_node_id(g::OSMGraph, x::DEFAULT_OSM_INDEX_TYPE)
index_to_node_id(g::OSMGraph, x::Vector{<:DEFAULT_OSM_INDEX_TYPE})
Maps node index to node id.
"""
index_to_node_id(g::OSMGraph, x::Integer) = g.index_to_node[x]
index_to_node_id(g::OSMGraph, x::Vector{<:Integer}) = [index_to_node_id(g, i) for i in x]
index_to_node_id(g::OSMGraph, x::DEFAULT_OSM_INDEX_TYPE) = g.index_to_node[x]
index_to_node_id(g::OSMGraph, x::Vector{<:DEFAULT_OSM_INDEX_TYPE}) = [index_to_node_id(g, i) for i in x]

"""
index_to_node(g::OSMGraph, x::Integer)
index_to_node(g::OSMGraph, x::Vector{<:Integer})
index_to_node(g::OSMGraph, x::DEFAULT_OSM_INDEX_TYPE)
index_to_node(g::OSMGraph, x::Vector{<:DEFAULT_OSM_INDEX_TYPE})
Maps node index to node object.
"""
index_to_node(g::OSMGraph, x::Integer) = g.nodes[g.index_to_node[x]]
index_to_node(g::OSMGraph, x::Vector{<:Integer}) = [index_to_node(g, i) for i in x]
index_to_node(g::OSMGraph, x::DEFAULT_OSM_INDEX_TYPE) = g.nodes[g.index_to_node[x]]
index_to_node(g::OSMGraph, x::Vector{<:DEFAULT_OSM_INDEX_TYPE}) = [index_to_node(g, i) for i in x]

"""
node_id_to_index(g::OSMGraph, x::Integer)
node_id_to_index(g::OSMGraph, x::Vector{<:Integer})
node_id_to_index(g::OSMGraph, x::DEFAULT_OSM_ID_TYPE)
node_id_to_index(g::OSMGraph, x::Vector{<:DEFAULT_OSM_ID_TYPE})
Maps node id to index.
"""
node_id_to_index(g::OSMGraph, x::Integer) = g.node_to_index[x]
node_id_to_index(g::OSMGraph, x::Vector{<:Integer}) = [node_id_to_index(g, i) for i in x]

node_id_to_index(g::OSMGraph, x::DEFAULT_OSM_ID_TYPE) = g.node_to_index[x]
node_id_to_index(g::OSMGraph, x::Vector{<:DEFAULT_OSM_ID_TYPE}) = [node_id_to_index(g, i) for i in x]
"""
node_to_index(g::OSMGraph, x::Node)
node_to_index(g::OSMGraph, x::Vector{Node})
Expand All @@ -35,38 +34,34 @@ node_to_index(g::OSMGraph, x::Node) = g.node_to_index[x.id]
node_to_index(g::OSMGraph, x::Vector{Node}) = [node_id_to_index(g, i.id) for i in x]

"""
index_to_dijkstra_state(g::OSMGraph, x::Integer)
index_to_dijkstra_state(g::OSMGraph, x::DEFAULT_OSM_INDEX_TYPE)
Maps node index to dijkstra state (parents).
"""
index_to_dijkstra_state(g::OSMGraph, x::Integer) = g.dijkstra_states[x]

index_to_dijkstra_state(g::OSMGraph, x::DEFAULT_OSM_INDEX_TYPE) = g.dijkstra_states[x]
"""
node_id_to_dijkstra_state(g::OSMGraph, x::Integer)
node_id_to_dijkstra_state(g::OSMGraph, x::DEFAULT_OSM_ID_TYPE)
Maps node id to dijkstra state (parents).
"""
node_id_to_dijkstra_state(g::OSMGraph, x::Integer) = g.dijkstra_states[node_id_to_index(g, x)]

node_id_to_dijkstra_state(g::OSMGraph, x::DEFAULT_OSM_ID_TYPE) = g.dijkstra_states[node_id_to_index(g, x)]
"""
set_dijkstra_state_with_index!(g::OSMGraph, index::Integer, state)
set_dijkstra_state_with_index!(g::OSMGraph, index::DEFAULT_OSM_INDEX_TYPE, state)
Set dijkstra state (parents) with node index.
"""
set_dijkstra_state_with_index!(g::OSMGraph, index::Integer, state) = push!(g.dijkstra_states, index, state)

set_dijkstra_state_with_index!(g::OSMGraph, index::DEFAULT_OSM_INDEX_TYPE, state) = push!(g.dijkstra_states, index, state)
"""
set_dijkstra_state_with_node_id!(g::OSMGraph, index::Integer, state)
set_dijkstra_state_with_node_id!(g::OSMGraph, index::DEFAULT_OSM_ID_TYPE, state)
Set dijkstra state (parents) with node id.
"""
set_dijkstra_state_with_node_id!(g::OSMGraph, node_id::Integer, state) = push!(g.dijkstra_states, node_id_to_index(g, node_id), state)

set_dijkstra_state_with_node_id!(g::OSMGraph, node_id::DEFAULT_OSM_ID_TYPE, state) = push!(g.dijkstra_states, node_id_to_index(g, node_id), state)
"""
maxspeed_from_index(g, x::Integer)
maxspeed_from_node_id(g, x::Integer)
maxspeed_from_index(g, x::DEFAULT_OSM_INDEX_TYPE)
maxspeed_from_node_id(g, x::DEFAULT_OSM_ID_TYPE)
Get maxspeed from index id or node id.
"""
maxspeed_from_index(g, x::Integer) = index_to_node(g, x).tags["maxspeed"]
maxspeed_from_node_id(g, x::Integer) = g.nodes[x].tags["maxspeed"]
maxspeed_from_index(g, x::DEFAULT_OSM_INDEX_TYPE) = index_to_node(g, x).tags["maxspeed"]
maxspeed_from_node_id(g, x::DEFAULT_OSM_ID_TYPE) = g.nodes[x].tags["maxspeed"]
8 changes: 4 additions & 4 deletions src/nearest_node.jl
Original file line number Diff line number Diff line change
Expand Up @@ -47,9 +47,9 @@ not included in the results.
Tuple elements are `Vector`sif a `Vector` of nodes is inputted, and numbers if a single point is inputted.
"""
nearest_node(g::OSMGraph, node::Node) = nearest_node(g, node.location, (index)->index==g.node_to_index[node.id])
nearest_node(g::OSMGraph, node_id::Integer) = nearest_node(g, g.nodes[node_id])
nearest_node(g::OSMGraph, node_id::DEFAULT_OSM_ID_TYPE) = nearest_node(g, g.nodes[node_id])
nearest_node(g::OSMGraph, nodes::Vector{<:Node}) = nearest_node(g, [n.id for n in nodes])
function nearest_node(g::OSMGraph, node_ids::AbstractVector{<:Integer})
function nearest_node(g::OSMGraph, node_ids::AbstractVector{<:DEFAULT_OSM_ID_TYPE})
locations = [g.nodes[n].location for n in node_ids]
cartesian_locations = to_cartesian(locations)
idxs, dists = knn(g.kdtree, cartesian_locations, 2, true)
Expand Down Expand Up @@ -106,9 +106,9 @@ Finds nearest nodes from a point or `Vector` of points using a `NearestNeighbors
Tuple elements are `Vector{Vector}` if a `Vector` of points is inputted, and `Vector` if a single point is inputted.
"""
nearest_nodes(g::OSMGraph, node::Node, n_neighbours::Integer=1) = nearest_nodes(g, node.location, n_neighbours, (index)->index==g.node_to_index[node.id])
nearest_nodes(g::OSMGraph, node_id::Integer, n_neighbours::Integer=1) = nearest_nodes(g, g.nodes[node_id], n_neighbours)
nearest_nodes(g::OSMGraph, node_id::DEFAULT_OSM_ID_TYPE, n_neighbours::Integer=1) = nearest_nodes(g, g.nodes[node_id], n_neighbours)
nearest_nodes(g::OSMGraph, nodes::Vector{<:Node}, n_neighbours::Integer=1) = nearest_nodes(g, [n.id for n in nodes], n_neighbours)
function nearest_nodes(g::OSMGraph, node_ids::Vector{<:Integer}, n_neighbours::Integer=1)
function nearest_nodes(g::OSMGraph, node_ids::Vector{<:DEFAULT_OSM_ID_TYPE}, n_neighbours::Integer=1)
locations = [g.nodes[n].location for n in node_ids]
n_neighbours += 1 # Closest node is always the input node itself, exclude self from result
cartesian_locations = to_cartesian(locations)
Expand Down
4 changes: 2 additions & 2 deletions src/nearest_way.jl
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,7 @@ Finds the nearest position on a way to a given point. Matches to an `EdgePoint`.
- `::EdgePoint`: Nearest position along the way between two nodes.
- `::Float64`: Distance from `point` to the nearest position on the way.
"""
function nearest_point_on_way(g::OSMGraph, point::GeoLocation, way_id::Integer)
function nearest_point_on_way(g::OSMGraph, point::GeoLocation, way_id::DEFAULT_OSM_ID_TYPE)
nodes = g.ways[way_id].nodes
min_edge = nothing
min_dist = floatmax()
Expand All @@ -122,4 +122,4 @@ function nearest_point_on_way(g::OSMGraph, point::GeoLocation, way_id::Integer)
end
end
return EdgePoint(min_edge[1], min_edge[2], min_pos), min_dist
end
end
13 changes: 9 additions & 4 deletions src/parse.jl
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,7 @@ is_restriction(tags::AbstractDict)::Bool = get(tags, "type", "") == "restriction
"""
Determine if a restriction is valid and has usable data.
"""
function is_valid_restriction(members::AbstractArray, ways::AbstractDict{T,Way{T}})::Bool where T <: Integer
function is_valid_restriction(members::AbstractArray, ways::AbstractDict{T,Way{T}})::Bool where T <: DEFAULT_OSM_ID_TYPE
role_counts = DefaultDict(0)
role_type_counts = DefaultDict(0)
ways_set = Set{Int}()
Expand Down Expand Up @@ -197,17 +197,18 @@ end
"""
Parse OpenStreetMap data into `Node`, `Way` and `Restriction` objects.
"""
function parse_osm_network_dict(osm_network_dict::AbstractDict,
function parse_osm_network_dict(id_type::Type,
osm_network_dict::AbstractDict,
network_type::Symbol=:drive;
filter_network_type::Bool=true
)::OSMGraph
U = DEFAULT_OSM_INDEX_TYPE
T = DEFAULT_OSM_ID_TYPE
T = id_type
W = DEFAULT_OSM_EDGE_WEIGHT_TYPE
L = DEFAULT_OSM_LANES_TYPE

ways = Dict{T,Way{T}}()
highway_nodes = Set{Int}([])
highway_nodes = Set{T}([])
for way in osm_network_dict["way"]
if haskey(way, "tags") && haskey(way, "nodes")
tags = way["tags"]
Expand Down Expand Up @@ -342,7 +343,9 @@ function init_graph_from_object(osm_xml_object::XMLDocument,
filter_network_type::Bool=true
)::OSMGraph
dict_to_parse = osm_dict_from_xml(osm_xml_object)
id_type = typeof(dict_to_parse["node"][1]["id"])
return parse_osm_network_dict(
id_type,
dict_to_parse,
network_type;
filter_network_type=filter_network_type
Expand All @@ -357,7 +360,9 @@ function init_graph_from_object(osm_json_object::AbstractDict,
filter_network_type::Bool=true
)::OSMGraph
dict_to_parse = osm_dict_from_json(osm_json_object)
id_type = typeof(dict_to_parse["node"][1]["id"])
return parse_osm_network_dict(
id_type,
dict_to_parse,
network_type;
filter_network_type=filter_network_type
Expand Down
20 changes: 10 additions & 10 deletions src/shortest_path.jl
Original file line number Diff line number Diff line change
Expand Up @@ -46,8 +46,8 @@ Calculates the shortest path between two OpenStreetMap node ids.
"""
function shortest_path(::Type{A},
g::OSMGraph{U,T,W},
origin::Integer,
destination::Integer,
origin::DEFAULT_OSM_ID_TYPE,
destination::DEFAULT_OSM_ID_TYPE,
weights::AbstractMatrix{W};
cost_adjustment::Function=(u, v, parents) -> 0.0,
max_distance::W=typemax(W)
Expand All @@ -60,8 +60,8 @@ function shortest_path(::Type{A},
end
function shortest_path(::Type{A},
g::OSMGraph{U,T,W},
origin::Integer,
destination::Integer,
origin::DEFAULT_OSM_ID_TYPE,
destination::DEFAULT_OSM_ID_TYPE,
weights::AbstractMatrix{W};
cost_adjustment::Function=(u, v, parents) -> 0.0,
heuristic::Function=distance_heuristic(g),
Expand All @@ -73,10 +73,10 @@ function shortest_path(::Type{A},
isnothing(path) && return
return index_to_node_id(g, path)
end
function shortest_path(::Type{A}, g::OSMGraph{U,T,W}, origin::Integer, destination::Integer; kwargs...)::Union{Nothing,Vector{T}} where {A <: PathAlgorithm, U, T, W}
function shortest_path(::Type{A}, g::OSMGraph{U,T,W}, origin::DEFAULT_OSM_ID_TYPE, destination::DEFAULT_OSM_ID_TYPE; kwargs...)::Union{Nothing,Vector{T}} where {A <: PathAlgorithm, U, T, W}
return shortest_path(A, g, origin, destination, g.weights; kwargs...)
end
function shortest_path(::Type{A}, g::OSMGraph{U,T,W}, origin::Node{<:Integer}, destination::Node{<:Integer}, args...; kwargs...)::Union{Nothing,Vector{T}} where {A <: PathAlgorithm, U, T, W}
function shortest_path(::Type{A}, g::OSMGraph{U,T,W}, origin::Node{<:DEFAULT_OSM_ID_TYPE}, destination::Node{<:DEFAULT_OSM_ID_TYPE}, args...; kwargs...)::Union{Nothing,Vector{T}} where {A <: PathAlgorithm, U, T, W}
return shortest_path(A, g, origin.id, destination.id, args...; kwargs...)
end
function shortest_path(g::OSMGraph{U,T,W}, args...; kwargs...)::Union{Nothing,Vector{T}} where {U, T, W}
Expand Down Expand Up @@ -217,7 +217,7 @@ hence we pick the largest maxspeed across all ways.
time_heuristic(g::OSMGraph) = (u, v) -> haversine(g.node_coordinates[u], g.node_coordinates[v]) / 100.0

"""
weights_from_path(g::OSMGraph{U,T,W}, path::Vector{T}; weights=g.weights)::Vector{W} where {U <: Integer,T <: Integer,W <: Real}
weights_from_path(g::OSMGraph{U,T,W}, path::Vector{T}; weights=g.weights)::Vector{W} where {U <: Integer,T <: DEFAULT_OSM_ID_TYPE,W <: Real}
Extracts edge weights from a path using the weight matrix stored in `g.weights` unless
a different matrix is passed to the `weights` kwarg.
Expand All @@ -230,12 +230,12 @@ a different matrix is passed to the `weights` kwarg.
# Return
- `Vector{W}`: Array of edge weights, distances are in km, time is in hours.
"""
function weights_from_path(g::OSMGraph{U,T,W}, path::Vector{T}; weights=g.weights)::Vector{W} where {U <: Integer,T <: Integer,W <: Real}
function weights_from_path(g::OSMGraph{U,T,W}, path::Vector{T}; weights=g.weights)::Vector{W} where {U <: Integer,T <: DEFAULT_OSM_ID_TYPE,W <: Real}
return [weights[g.node_to_index[path[i]], g.node_to_index[path[i + 1]]] for i in 1:length(path) - 1]
end

"""
total_path_weight(g::OSMGraph{U,T,W}, path::Vector{T}; weights=g.weights)::W where {U <: Integer,T <: Integer,W <: Real}
total_path_weight(g::OSMGraph{U,T,W}, path::Vector{T}; weights=g.weights)::W where {U <: Integer,T <: DEFAULT_OSM_ID_TYPE,W <: Real}
Extract total edge weight along a path.
Expand All @@ -247,7 +247,7 @@ Extract total edge weight along a path.
# Return
- `sum::W`: Total path edge weight, distances are in km, time is in hours.
"""
function total_path_weight(g::OSMGraph{U,T,W}, path::Vector{T}; weights=g.weights)::W where {U <: Integer,T <: Integer,W <: Real}
function total_path_weight(g::OSMGraph{U,T,W}, path::Vector{T}; weights=g.weights)::W where {U <: Integer,T <: DEFAULT_OSM_ID_TYPE,W <: Real}
sum::W = zero(W)
for i in 1:length(path) - 1
sum += weights[g.node_to_index[path[i]], g.node_to_index[path[i + 1]]]
Expand Down
Loading

0 comments on commit 18e73d4

Please sign in to comment.