Skip to content

Commit

Permalink
Merge pull request #153 from flow-project/multi_lane_bug_fix
Browse files Browse the repository at this point in the history
Multi lane bug fix
  • Loading branch information
AboudyKreidieh committed Sep 18, 2018
2 parents b34cf54 + d0935c3 commit fb4195a
Show file tree
Hide file tree
Showing 7 changed files with 316 additions and 45 deletions.
4 changes: 2 additions & 2 deletions examples/sumo/highway.py
Original file line number Diff line number Diff line change
Expand Up @@ -46,13 +46,13 @@ def highway_example(render=None):
inflow = InFlows()
inflow.add(
veh_type="human",
edge="highway",
edge="highway_0",
probability=0.25,
departLane="free",
departSpeed=20)
inflow.add(
veh_type="human2",
edge="highway",
edge="highway_0",
probability=0.25,
departLane="free",
departSpeed=20)
Expand Down
34 changes: 18 additions & 16 deletions flow/core/vehicles.py
Original file line number Diff line number Diff line change
Expand Up @@ -190,25 +190,25 @@ def add(self,

self.initial.append({
"veh_id":
veh_id,
veh_id,
"acceleration_controller":
acceleration_controller,
acceleration_controller,
"lane_change_controller":
lane_change_controller,
lane_change_controller,
"routing_controller":
routing_controller,
routing_controller,
"initial_speed":
initial_speed,
initial_speed,
"num_vehicles":
num_vehicles,
num_vehicles,
"speed_mode":
speed_mode,
speed_mode,
"lane_change_mode":
lane_change_mode,
lane_change_mode,
"sumo_car_following_params":
sumo_car_following_params,
sumo_car_following_params,
"sumo_lc_params":
sumo_lc_params
sumo_lc_params
})

# this is used to return the actual headways from the vehicles class
Expand Down Expand Up @@ -1119,7 +1119,7 @@ def _multi_lane_headways_util(self, veh_id, edge_dict, num_edges, env):
edge_dict : dict < list<tuple> >
Key = Edge name
Index = lane index
Element = sorted list of (vehicle id, position)
Element = list sorted by position of (vehicle id, position)
Returns
-------
Expand All @@ -1138,6 +1138,7 @@ def _multi_lane_headways_util(self, veh_id, edge_dict, num_edges, env):
"""
this_pos = self.get_position(veh_id)
this_edge = self.get_edge(veh_id)
this_lane = self.get_lane(veh_id)
num_lanes = env.scenario.num_lanes(this_edge)

# set default values for all output values
Expand All @@ -1156,7 +1157,8 @@ def _multi_lane_headways_util(self, veh_id, edge_dict, num_edges, env):

# if you are at the end or the front of the edge, the lane
# leader is in the edges in front of you
if index < len(positions) - 1:
if (lane == this_lane and index < len(positions) - 1) \
or (lane != this_lane and index < len(positions)):
# check if the index does not correspond to the current
# vehicle
if ids[index] == veh_id:
Expand All @@ -1165,15 +1167,15 @@ def _multi_lane_headways_util(self, veh_id, edge_dict, num_edges, env):
self.get_length(leader[lane]))
else:
leader[lane] = ids[index]
headway[lane] = positions[index] - this_pos \
- self.get_length(leader[lane])
headway[lane] = (positions[index] - this_pos
- self.get_length(leader[lane]))

# you are in the back of the queue, the lane follower is in the
# edges behind you
if index > 0:
follower[lane] = ids[index - 1]
tailway[lane] = this_pos - positions[index - 1] \
- self.get_length(veh_id)
tailway[lane] = (this_pos - positions[index - 1]
- self.get_length(veh_id))

# if lane leader not found, check next edges
if leader[lane] == "":
Expand Down
12 changes: 8 additions & 4 deletions flow/scenarios/base_scenario.py
Original file line number Diff line number Diff line change
Expand Up @@ -128,7 +128,11 @@ def __init__(self,
])

# generate starting position for vehicles in the network
positions, lanes = self.generate_starting_positions()
kwargs = initial_config.additional_params
positions, lanes = self.generate_starting_positions(
num_vehicles=vehicles.num_vehicles,
**kwargs
)

# create the sumo configuration files using the generator class
cfg_name = self.generator.generate_cfg(self.net_params,
Expand Down Expand Up @@ -403,7 +407,7 @@ def gen_random_start_pos(self, initial_config, num_vehicles, **kwargs):
"""
(x0, min_gap, bunching, lanes_distr, available_length,
available_edges, initial_config) = self._get_start_pos_util(
initial_config, num_vehicles, **kwargs)
initial_config, num_vehicles, **kwargs)

# extra space a vehicle needs to cover from the start of an edge to be
# fully in the edge and not risk having a gap with a vehicle behind it
Expand Down Expand Up @@ -433,7 +437,7 @@ def gen_random_start_pos(self, initial_config, num_vehicles, **kwargs):
for i in range(num_vehicles):
edge_i = available_edges[edge_indx]
pos_i = (init_absolute_pos[i] - decrement) % (
self.edge_length(edge_i) - efs)
self.edge_length(edge_i) - efs)
lane_i = int(((init_absolute_pos[i] - decrement) - pos_i) /
(self.edge_length(edge_i) - efs))

Expand All @@ -446,7 +450,7 @@ def gen_random_start_pos(self, initial_config, num_vehicles, **kwargs):

edge_i = available_edges[edge_indx]
pos_i = (init_absolute_pos[i] - decrement) % (
self.edge_length(edge_i) - efs)
self.edge_length(edge_i) - efs)

lane_i = int(((init_absolute_pos[i] - decrement) - pos_i) /
(self.edge_length(edge_i) - efs))
Expand Down
45 changes: 27 additions & 18 deletions flow/scenarios/highway/gen.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
"""Contains the highway scenario class."""

from flow.core.generator import Generator
import numpy as np


class HighwayGenerator(Generator):
Expand All @@ -20,30 +21,34 @@ def __init__(self, net_params, base):
def specify_nodes(self, net_params):
"""See parent class."""
length = net_params.additional_params["length"]
num_edges = net_params.additional_params.get("num_edges", 1)
segment_lengths = np.linspace(0, length, num_edges+1)

nodes = [{
"id": "begin",
"x": repr(0),
"y": repr(0)
}, {
"id": "end",
"x": repr(length),
"y": repr(0)
}]
nodes = []
for i in range(num_edges+1):
nodes += [{
"id": "edge_{}".format(i),
"x": repr(segment_lengths[i]),
"y": repr(0)
}]

return nodes

def specify_edges(self, net_params):
"""See parent class."""
length = net_params.additional_params["length"]

edges = [{
"id": "highway",
"type": "highwayType",
"from": "begin",
"to": "end",
"length": repr(length)
}]
num_edges = net_params.additional_params.get("num_edges", 1)
segment_length = length/float(num_edges)

edges = []
for i in range(num_edges):
edges += [{
"id": "highway_{}".format(i),
"type": "highwayType",
"from": "edge_{}".format(i),
"to": "edge_{}".format(i+1),
"length": repr(segment_length)
}]

return edges

Expand All @@ -62,6 +67,10 @@ def specify_types(self, net_params):

def specify_routes(self, net_params):
"""See parent class."""
rts = {"highway": ["highway"]}
num_edges = net_params.additional_params.get("num_edges", 1)
rts = {}
for i in range(num_edges):
rts["highway_{}".format(i)] = ["highway_{}".format(j) for
j in range(i, num_edges)]

return rts
29 changes: 28 additions & 1 deletion flow/scenarios/highway/scenario.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,8 @@
"lanes": 4,
# speed limit for all edges
"speed_limit": 30,
# number of edges to divide the highway into
"num_edges": 1
}


Expand Down Expand Up @@ -39,11 +41,36 @@ def __init__(self,

self.length = net_params.additional_params["length"]
self.lanes = net_params.additional_params["lanes"]
self.num_edges = net_params.additional_params.get("num_edges", 1)

super().__init__(name, generator_class, vehicles, net_params,
initial_config, traffic_lights)

def specify_edge_starts(self):
"""See parent class."""
edgestarts = [("highway", 0)]
edgestarts = [("highway_{}".format(i), 0)
for i in range(self.num_edges)]
return edgestarts

def gen_custom_start_pos(self, initial_config, num_vehicles, **kwargs):
"""Generate a user defined set of starting positions.
This method is just used for testing.
Parameters
----------
initial_config : InitialConfig type
see flow/core/params.py
num_vehicles : int
number of vehicles to be placed on the network
kwargs : dict
extra components, usually defined during reset to overwrite initial
config parameters
Returns
-------
startpositions : list of tuple (float, float)
list of start positions [(edge0, pos0), (edge1, pos1), ...]
startlanes : list of int
list of start lanes
"""
return kwargs["start_positions"], kwargs["start_lanes"]

0 comments on commit fb4195a

Please sign in to comment.