通常,netconvert 和 netgenerate 在计算网络时会生成路口的交通信号灯及其控制方案。然而,这些计算出的控制方案往往与现实中的有所不同。 为了在仿真中使用真实的交通信号灯控制方案,可以在运行 sumo/sumo-gui 时加载额外的控制方案定义。此外, sumo/sumo-gui 允许加载描述一组交通信号灯何时以及如何从一个控制方案切换到另一个的定义。这两点将在接下来的章节中讨论。另一种可能性是在 netedit 中可视化地编辑交通信号灯计划。
自动生成的 TLS 控制方案#
- 默认情况下,所有交通信号灯都生成为固定周期,周期时间为 90 秒。这可以通过选项 --tls.cycle.time 更改。osmWebWizard 默认生成 感应式 (actuated) 交通信号灯(见下文)。
- 绿灯时间在主要相位之间平均分配。
- 所有绿灯相位后都跟随一个黄灯相位。黄灯相位的长度根据进入道路的最大速度计算,但可以通过选项 --tls.yellow.time 自定义。
- 如果交叉口的速度低于 70km/h 的阈值(可通过选项 tls.minor-left.max-speed 配置),左转车辆可以与对向直行车辆同时通行,但必须让行。这被称为 次要绿灯 (green minor),并在状态定义中用小写 g 表示。否则,左转车流必须使用受保护的左转相位(见下文)。如果由于没有专用左转车道而无法构建此类相位,则仍然允许 次要绿灯,但会发出警告。
- 如果一个绿灯相位允许部分冲突的车流(即直行和对向左转)同时通行,并且存在专用转弯车道,则其后会跟随另一个绿灯相位,该相位对部分冲突的车流拥有完全优先权(这通常是一个左转相位)。该相位的持续时间默认为 6 秒,可以通过设置选项 --tls.left-green.time 进行自定义(或禁用)。
- 默认情况下,生成的周期在时间 0 以第一个主要方向(按道路优先级、车道数量和速度排序)的绿灯相位开始。这可以通过为指定的交通信号灯 ID 列表使用选项 --tls.half-offset TLS1,TLS2,.. 和 --tls.quarter-offset TLS3,TLS4,... 来影响(将第一个相位的开始时间偏移周期时间的指示分数)。
- 在现实中,通常会有所有车流都为红灯的相位,以清空交叉口。SUMO 默认不构建这些相位。要使每个绿灯相位前都有一个全红相位,可以使用选项 --tls.allred.time。
- 也可以通过设置选项 --tls.default-type 来生成 感应式交通信号灯。这将生成与上述相同的信号计划,但绿灯相位的长度是可变的,范围为 5 秒至 50 秒(这两个值可以使用选项 --tls.min-dur, --tls.max-dur 设置)。 - 默认类型 actuated:交通信号灯的感应基于自动生成的感应线圈测量的间隔。 - 默认类型 delay_based:感应基于车辆的延误。
- 可以通过设置选项 --tls.layout 为 opposites(默认)或 incoming(见下文)来选择生成的相位布局。
- 生成的相位布局也受节点类型的影响,节点类型可以是 traffic_light 或 traffic_light_right_on_red(如下所述)。
默认的四路交叉口(布局 opposites)#
默认情况下,控制方案生成 4 个绿灯相位:
- 一个直行相位。
- 一个左转相位(仅当存在专用左转车道时)。
- 与第一个方向正交方向的直行相位。
- 与第一个方向正交方向的左转相位(仅当存在专用左转车道时)。
根据上述默认定时,绿灯相位的持续时间通常为 31 秒。
如果节点类型设置为 traffic_light_right_on_red 而不是 traffic_light,则所有方向的右转在所有相位都是允许的(在进入当前拥有绿灯的车流之前必须停车)。
相位布局 incoming#
- 交叉口的每个进入边都获得一个单独的绿灯相位,允许所有方向的移动。
- 如果节点类型设置为 traffic_light_right_on_red 而不是 traffic_light,则兼容的右转可以同时进行。
相位布局 alternateOneWay#
此布局可用于模拟对道路路段的交替访问,该路段一次只能被一个方向使用。 要使用此布局,必须为所有与受限路段接壤的路口以及位于其内的所有路口定义一个联合交通信号灯。交替的绿灯相位由一个足够长的全红相位分隔,以清空内部路段。
其他相位布局#
- 如果在交叉口相遇的道路超过 4 条,则会生成额外的绿灯相位。
- 如果在交叉口相遇的道路在转弯车流上具有最高的道路优先级,则可能会生成布局 incoming 而不是布局 opposites。
- 如果一个交通信号灯路口没有任何冲突的道路(即它模拟的是一个人行横道),默认情况下它不会获得红灯相位。可以通过设置选项 --tls.red.time 来生成一个红灯相位。
利用交通需求知识改进生成的控制方案#
使用感应式交通信号灯#
要获得能动态适应需求的交通信号灯,请在构建网络时使用选项 --tls.default-type actuated。这将自动生成感应式交通信号灯。
注意
如果网络是由 osmWebWizard.py 创建的,则交通信号灯默认为 'actuated'。
要将现有的 .net.xml 文件转换为所有交通信号灯都是感应式的,请执行以下调用:
netconvert -s orig.net.xml --o new.net.xml --tls.rebuild --tls.default-type actuated
调整固定定时(绿信比)以适应已知交通#
tlsCycleAdaptation.py 可用于修改绿灯相位持续时间以适应给定的交通需求。
协调固定定时#
工具 tlsCoordinator.py 可用于修改控制方案的偏移量,以为给定的交通需求生成绿波。
定义新的 TLS 控制方案#
可以将交通信号灯的新定义作为 additional-file 的一部分加载。加载后,将使用最后一个控制方案。可以通过 WAUT 和/或 TraCI 在控制方案之间切换。也可以使用 GUI 上下文菜单在它们之间切换。additional-file 中的交通信号灯控制方案定义如下所示:
<additional>
<tlLogic id="0" programID="my_program" offset="0" type="static">
<phase duration="31" state="GGggrrrrGGggrrrr"/>
<phase duration="5" state="yyggrrrryyggrrrr"/>
<phase duration="6" state="rrGGrrrrrrGGrrrr"/>
<phase duration="5" state="rryyrrrrrryyrrrr"/>
<phase duration="31" state="rrrrGGggrrrrGGgg"/>
<phase duration="5" state="rrrryyggrrrryygg"/>
<phase duration="6" state="rrrrrrGGrrrrrrGG"/>
<phase duration="5" state="rrrrrryyrrrrrryy"/>
</tlLogic>
</additional>
注意
为了快速上手,您可以从 .net.xml 文件中复制要编辑的所有交通信号灯的 tlLogic 元素,并将其放入一个新文件中。然后您只需要更改 programID 属性,该控制方案就可以被修改和加载了。
<tlLogic> 属性#
tlLogic 元素中使用以下属性/元素:
| 属性名称 | 值类型 | 描述 |
|---|---|---|
| id | id (字符串) | 交通信号灯的 id。这必须是 .net.xml 文件中现有的交通信号灯 id。通常,交通信号灯的 id 与路口 id 相同。可以通过右键单击受控交叉口前方的红/绿条来获取名称。 |
| type | 枚举 (static, actuated, delay_based) | 交通信号灯的类型(固定相位持续时间、基于车辆之间时间间隔延长相位(actuated),或基于排队车辆累积时间损失(delay_based)) |
| programID | id (字符串) | 交通信号灯控制方案的 id;这必须是该交通信号灯 id 的新控制方案名称。请注意,"off" 是保留的,见下文。 |
| offset | int 或 "begin" | 控制方案的初始时间偏移,如果设置为 "begin",偏移将自动匹配仿真开始时间,以便交通信号灯总是从相位 0 开始。 |
<phase> 属性#
每个相位使用以下属性定义:
| 属性名称 | 值类型 | 描述 |
|---|---|---|
| duration | 时间 (int) | 相位的持续时间 |
| state | 信号状态列表 | 该相位的交通信号灯状态,见下文 |
| minDur | 时间 (int) | 当使用 actuated 类型时,相位的最小持续时间。可选,默认为 duration。 |
| maxDur | 时间 (int) | 当使用 actuated 类型时,相位的最大持续时间。可选,如果 minDur 未设置则默认为 duration,否则默认为 2147483。 |
| name | 字符串 | 相位的可选描述。可用于建立 SUMO 相位索引与交通工程相位名称之间的对应关系。 |
| next | 相位索引列表 (int ...) | 当前相位之后周期中的下一个相位。这在向交通信号灯计划添加额外的过渡相位时非常有用,这些相位并非每个周期的一部分。'actuated' 类型的交通信号灯可以利用索引列表在备选后继相位中进行选择。 |
注意
在 SUMO-TLS 定义中,时间在垂直轴上,每个相位描述了持续固定时长的所有信号状态。这与典型的交通工程图不同,后者时间在水平轴上,每一行描述一个信号的状态。另一个关键区别是,在 SUMO 中,只要至少一个信号改变其状态,就会引入一个新相位。这意味着绿灯相位之间的过渡可以由多个中间相位组成。
信号状态定义#
相位状态中的每个字符描述交通信号灯一个信号的状态。请注意,一个车道可能包含多个信号——例如,一个用于左转车辆,一个用于直行车辆。这意味着信号不控制车道,而是控制连接(link)——每个连接将进入路口的车道与离开该路口的车道连接起来。在 SUMO 中,实现了信号与连接之间的一对多依赖关系,这意味着一个信号可以控制多个连接——尽管由 netconvert 或 netgenerate 生成的网络通常每个连接使用一个信号。另请注意,一个交通信号灯可以控制进入不同路口的车道。关于哪个连接由哪个交通信号灯信号控制的信息,可以使用 sumo-gui 可视化设置中的 "show link tls index" 选项或根据 .net.xml 文件中 <connection> 元素的 linkIndex 属性获取。
使用以下信号颜色:
| 字符 | GUI 颜色 | 描述 |
|---|---|---|
| r | FOO | 信号的 '红灯' - 车辆必须停车 |
| y | FOO | 信号的 '琥珀色(黄)灯' - 如果离路口较远,车辆将开始减速,否则它们会通过 |
| g | FOO | 信号的 '绿灯',无优先权 - 如果没有车辆使用更高优先级的冲突车流,车辆可以通过路口,否则它们会减速让行。它们在接近时总是会减速,直到进入配置的可见距离 |
| G | FOO | 信号的 '绿灯',有优先权 - 车辆可以通行路口 |
| s | FOO | '绿色右转箭头' 需要停车 - 如果没有车辆使用更高优先级的冲突车流,车辆可以通过路口。它们在通过前总是会停车。这只为路口类型 traffic_light_right_on_red 生成。 |
| u | FOO | 信号的 '红+黄灯',可用于指示即将到来的绿灯相位,但车辆还不能行驶(在 GUI 中显示为橙色) |
| o | FOO | '关闭 - 闪烁' 信号已关闭,闪烁灯表示车辆必须让行 |
| O | FOO | '关闭 - 无信号' 信号已关闭,车辆拥有通行权 |

示例:当前状态为 "GrGr" 的交通信号灯。最左边的字母 "G" 编码了连接 0 的绿灯,后面是连接 1 的红灯,连接 2 的绿灯和连接 3 的红灯。连接编号可以通过激活 show link tls index 在 sumo-gui 设置 中启用。
默认连接索引#
对于控制单个交叉口的交通信号灯,默认的由 netconvert 生成的索引按顺时针模式编号,从 12 点钟方向开始为 0,右转排在直行连接之前,左转之后。人行横道总是被分配在最后,同样按顺时针方式。
如果交通信号灯被连接,使得单个控制方案控制多个交叉口,则每个交叉口的顺序保持不变,但索引会根据输入文件中受控路口的顺序递增。
以编程方式访问索引#
TLS 连接索引可以使用以下方式访问:
- sumolib 使用 connection.getTLLinkIndex()
- sumolib 使用 tls.getConnections()
- 或 TraCI 使用 traci.trafficlight.getControlledLinks()
图形化查看 TLS 控制方案#
在 sumo-gui 中,您可以右键单击红/绿停车条并选择 show phases。
信号计划与通行权规则之间的相互作用#
每个交通信号灯路口都有一个优先级路口的通行权规则作为基础。当关闭交通信号灯时(在 sumo-gui 中右键单击交通信号灯或通过加载 "off" 控制方案),这一点变得显而易见。
当定义具有同时冲突绿灯车流的信号计划时(通过使用 g 和 G 状态),该优先级路口的通行权规则就会发挥作用。这些信号计划只有在通行权规则强制 g 车流的车辆让行 G 车流的情况下才能正常工作。在大多数情况下,这种关系在默认信号计划中已正确设置。
然而,当引入新的 g/G 关系时,只有将网络和新的信号计划加载到 netconvert 中并因此更新通行权规则,才能确保正确性。
具有固定定时的交通信号灯#
SUMO 中最简单的交通信号灯类型具有固定定时,并使用 <tlLogic> 属性 type="static" 声明。
这种类型的交通信号灯将循环遍历固定的状态序列,并根据每个状态的 duration 属性在每个状态停留相应的时间。
默认情况下,相位顺序将按照输入文件中相位元素的顺序进行,最后一个相位结束后重新从第一个相位开始。
可以通过为部分或所有相位定义属性 next 来改变相位的顺序(如果在 next 中定义了多个索引,则使用第一个条目,其余的将被忽略)。
响应交通的交通信号灯#
通常,“感应式 (actuated)”这个名称指的是响应交通(或缺乏交通)而切换的交通信号灯。不同的控制器及其功能如下所述。SUMO 支持多种具有此特性的算法,将在下面描述。
注意
介观仿真 不支持感应式交通信号灯。
类型 'actuated'#
SUMO 支持基于间隔 (gap-based) 的感应式交通控制。这种控制方案在德国很常见,其工作原理是每当检测到连续的交通流时就延长交通相位。它在检测到连续车辆之间有足够的时间间隔后切换到下一个相位。这允许在相位之间更好地分配绿灯时间,并且还会影响周期持续时间以响应动态交通状况。
要使用这种类型的控制,<tlLogic>-元素需要接收属性 type="actuated"。它还需要使用 phase-属性 minDur 和 maxDur 来代替 duration,以定义每个相位允许的时间持续时间范围(如果这些值相等或只给出了 duration,则该相位将具有恒定的持续时间)。可以使用附加参数来进一步配置控制算法。这些参数可以在 <tlLogic>-元素内给出,如下所示:
检测器#
决定相位延长的时间间隔由感应线圈检测器收集。这些检测器以可配置的距离(见下文)自动放置。如果进入车道太短,并且存在一系列唯一的前置车道,则检测器将被放置在计算距离处的前置车道上。
检测器名称的形式为 TLSID_PROGRAMID_EDGEINDEX.LANEINDEX,其中
- TLSID 是 tlLogic 元素的 id
- PROGRAMID 是属性 'programID' 的值
- EDGEINDEX 是一个从 0 开始的运行索引,对应于接近 tls linkIndex 0 的边(通常是北向入口)
- LANEINDEX 是当前边的运行索引,从第一个车辆车道开始(人行道不计数)
每个进入交通信号灯的车道都会获得一个检测器。然而,并非所有检测器都能在所有相位中使用。 在当前实现中,仅当检测器车道的所有连接在特定相位中获得无条件绿灯 ('G') 时,才使用感应检测器。这样做是为了防止在给定车道上的第一辆车不允许行驶时进行无用的相位延长。一个简单的解决方法通常是提供专用的左转车道。
注意
如果某个相位或连接索引没有可用的检测器,Sumo 会发出 "... has no controlling detector" 形式的警告。
注意
当将选项 --tls.actuated.jam-threshold 设置为大于 0 的值(例如 30)时,所有检测器都将可用,因为如果发现检测器拥堵,会自动避免无用的相位延长。或者,这可以为单个 tls (<param key="jam-threshold" value="30">) 甚至单个车道配置,使用 <param key="jam-threshold:LANEID" value="30">,将 <param> 元素放入 <tlLogic> 定义中。
检测器激活状态可以选择性地写入 TLS 输出。
示例#
<tlLogic id="0" programID="my_program" offset="0" type="actuated">
<param key="max-gap" value="3.0"/>
<param key="detector-gap" value="2.0"/>
<param key="passing-time" value="2.0"/>
<param key="vTypes" value=""/>
<param key="show-detectors" value="false"/>
<param key="file" value="NUL"/>
<param key="freq" value="300"/>
<param key="jam-threshold" value="-1"/>
<param key="detector-length" value="0"/>
<param key="build-all-detectors" value="false"/>
<phase duration="31" minDur="5" maxDur="45" state="GGggrrrrGGggrrrr"/>
...
</tlLogic>
参数#
可以使用几个可选参数来控制感应式交通信号灯的行为。上一节中的示例值是这些参数的默认值,其含义如下:
- max-gap:连续车辆之间的最大时间间隔,超过此间隔当前相位将被延长(在 maxDur 限制内)。
- detector-gap:确定(自动生成的)检测器与停车线之间的时间距离(以秒为单位)(按每个车道的最大速度计算)。
- passing-time:估计车辆通过停车线时的车头时距。这根据公式
(minDur / passingTime + 0.5) * 7.5设置检测器与停车线之间距离的上限。此限制的目的是允许检测器和停车线之间的所有车辆在 minDur 时间内通过交叉口。如果 minDur 给出的清空时间不足,将发出警告。 - linkMaxDur:X(其中 X 是交通信号灯索引):这将设置一个附加的最大持续时间标准,该标准基于单个信号的绿灯持续时间,而不是相位持续时间。
- linkMinDur:X(其中 X 是交通信号灯索引):这将设置一个附加的最小持续时间标准,该标准基于单个信号的绿灯持续时间,而不是相位持续时间。
- show-detectors 控制生成的检测器在 sumo-gui 中是可见还是隐藏。所有交通信号灯的默认值可以通过选项 --tls.actuated.show-detectors 设置。也可以通过在 GUI 中右键单击交通信号灯来切换此值。
- 参数 vTypes, file 和 freq 与常规感应线圈检测器具有相同的含义。
- coordinated (true/false) 在使用协调时影响时间周期中的参考点。
- cycleTime 设置使用协调时的周期时间(以秒为单位)。默认为所有相位 'durations' 值的总和。
- jam-threshold:如果检测到的车辆在检测器上停留了给定时间或更长时间,则忽略它们。
- jam-threshold:LANEID:如果检测到的车辆在给定 LANEID 的检测器上停留了给定时间或更长时间,则忽略它们。
- detector-length:将检测器长度设置为给定值(以确保在不同间隔和车辆位置下都能稳健地检测请求)。
- build-all-detectors:为所有进入车道构建检测器,即使它们不会控制感应相位。
某些参数仅在使用动态相位选择的信号计划时才使用:
- inactive-threshold(默认 180):该参数设置时间(以秒为单位),超过此时间后,非活动相位将被优先选择。
- linkMinDur:X(其中 X 是交通信号灯索引):这将设置一个附加的最小持续时间标准,该标准基于单个信号而不是相位持续时间。
可视化#
通过设置 sumo 选项 --tls.actuated.show-detectors 可以设置检测器的默认可见性。此外,在 sumo-gui 中,可以通过右键单击感应式交通信号灯并选择相应的菜单项来显示/隐藏检测器。
感应式交通信号灯使用的检测器将被着色以指示其状态:
- 绿色表示检测器用于确定当前相位的长度。
- 白色表示检测器在当前相位中未被使用。
- 红色表示自受控连接在该车道上最后一次亮绿灯以来,检测器检测到了车辆(仅当这些连接当前为红灯时)。
- 洋红色表示活动的覆盖。
自定义检测器#
要使用自定义检测器(例如用于自定义放置或输出),可以定义附加参数,其中 KEY 是进入交通信号灯的车道,VALUE 是用户定义的 inductionLoop(也可以位于另一个上游车道上)。
<param key="gneE42_2" value="customDetector1"/>
通过分配特殊值 NO_DETECTOR,可以完全禁用给定车道键的检测器。
注意
自定义检测器仅在 'tlLogic' 从附加文件加载时才有效。
自定义检测器激活状态可以选择性地写入 TLS 输出。
为了在输出和相位跟踪器对话框中包含更多检测器(例如,当自定义逻辑使用车道区域检测器或同一车道上的多个检测器时),可以使用以下声明来列出所有额外检测器:
<param key="extra-detectors" value="customDetector1 customDetector2 ..."/>
车道特定的检测器设置#
要定义与默认值不同的 max-gap 值,可以使用 key="max-gap:<LANE_ID>" 的参数,其中 LANE_ID 是进入交通信号灯的车道(检测器可能位于更上游)。
<param key="max-gap:gneE42_2" value="2"/>
同样,可以设置自定义的 jam-threshold 或 detector-length:
<param key="jam-threshold:LANE_ID" value="5"/>
<param key="detector-length:LANE_ID" value="2.5"/>
协调#
感应相位(minDur != maxDur)可以通过添加属性 'earliestEnd' 和 'latestEnd' 来协调。 如果使用这些值,则交通信号灯计划中的每一步都会被分配一个 'timeInCycle' 值,具体取决于参数 'coordinated'(默认为 'false')的值。
- coordinated=true: timeInCycle = (simulationTime - offset) % cycleTime(其中 cycleTime 取自 key=cycleTime 的参数)
- coordinated=false: timeInCycle = 自上次切换到相位 0 以来的时间
如果设置了 'earliestEnd',则在 timeInCycle < earliestEnd 时,相位不能结束(有效地增加 minDur)。 如果设置了 'latestEnd',则在 timeInCycle = latestEnd 时,相位不能延长(有效地减少 maxDur)。
当设置 'latestEnd' < 'earliestEnd' 时,相位可以延长到下一个周期。 如果两个值都已定义,并且相位已经在当前周期中开始和结束,则两个值都将被移至下一个周期,以避免相位在同一周期内运行多次(这只发生在参数 'coordinated' 设置为 'true' 时)。
<tlLogic id="0" programID="my_program" offset="10" type="actuated">
<param key="coordinated" value="true"/>
<param key="cycleTime" value="60"/>
<phase duration="31" minDur="5" maxDur="45" state="GGggrrrrGGggrrrr" earliestEnd="10" latestEnd="50"/>
...
</tlLogic>
动态相位选择(相位跳过)#
当一个相位使用带有索引列表的 'next' 属性时。下一个相位是根据所有候选相位的检测器状态动态选择的,算法如下:
- 计算 'next' 中给出的每个相位的优先级。优先级主要由该相位的活动检测器数量决定。活动意味着以下任一情况:
- 检测间隔低于阈值
- 自该检测器之后的信号上次为绿灯以来有检测
- 对于目标相位中将变为绿灯的每个交叉口,如果有接近的行人,则为该相位分配大量奖励优先级。
- 只要其 maxDur 未达到,当前相位就隐式可用于延续。当前相位的检测器获得奖励优先级。
- 使用优先级最高的相位,'next' 列表中靠前的相位优先于靠后的相位。
- 如果没有交通,相位将运行由 'next' 属性中的第一个值定义的默认周期
- 如果交通信号灯使用自定义切换规则,则默认相位是 'next' 属性的最后一个值。
- 如果某个特定相位应在没有交通的情况下无限期保持活动状态,则它必须在 'next' 列表中拥有自己的索引以及较高的 maxDur 值。
- 如果某个活动检测器在给定的时间阈值(参数 inactive-threshold)内未被服务,则该检测器会根据其未被服务的时间获得奖励优先级。这可用于防止其他相位因服务更多交通而持续被优先选择时发生饥饿。
此类交通信号灯逻辑的示例可在 <SUMO_HOME>/tests/sumo/tls/actuated/multiNext/dualring_simple 中找到。
辅助脚本 buildTransitions.py 可用于从简化定义生成此类逻辑。
示例:左转相位可以被跳过#
<tlLogic id="C" type="actuated" programID="P1" offset="0">
<phase duration="33" state="GgrrGgrr" minDur="5" maxDur="60" next="8 1"/>
<phase duration="3" state="ygrrygrr"/>
<phase duration="6" state="rGrrrGrr" minDur="5" maxDur="60" />
<phase duration="3" state="ryrrryrr"/>
<phase duration="33" state="rrGgrrGg" minDur="5" maxDur="60" next="9 5"/>
<phase duration="3" state="rrygrryg"/>
<phase duration="6" state="rrrGrrrG" minDur="5" maxDur="60" />
<phase duration="3" state="rrryrrry" next="0"/>
<phase duration="3" state="yyrryyrr" next="4"/>
<phase duration="3" state="rryyrryy"/>
</tlLogic>
类型 'actuated',带有自定义切换规则#
默认情况下,所有交通信号灯控制方案都由相同的预定义规则管理,这些规则决定了在每个相位中使用或忽略哪些检测器。如果需要更大的灵活性,可以通过使用相位属性 'earlyTarget' 和 'finalTarget' 来定义逻辑表达式。
如果控制器处于感应相位(minDur < maxDur)并且可以切换到新相位,则评估新相位的 'earlyTarget' 属性。如果表达式评估为 'true',则控制器切换到新相位。否则它将保留在当前相位。如果当前相位有多个后继(属性 'next'),则从左到右评估候选者,并使用第一个 'earlyTarget' 评估为 true 的候选者。
如果控制器已达到当前相位的最大持续时间,并且使用属性 'next' 定义了多个后继相位,则从左到右评估所有候选相位的 'finalTarget' 属性。使用第一个表达式评估为 'true' 的相位。否则,使用 next-list 中最右边的相位。
以下元素允许用于 'earlyTarget' 和 'finalTarget' 属性的表达式:
- 数字
- 比较符 >,=,>=
- 数学运算符 +,-,,/,*,%
- 逻辑运算符 'or', 'and', '!'
- 括号 (,)
- 预定义函数:
- 'z:DETID':返回感应线圈检测器(id 为 'DETID' 或 'TLSID_PROGRAMID_DETID')自上次车辆检测以来的时间间隔(DETID 可以省略前缀 'TLSID_PROGRAMID_')
- 'a:DETID':返回 id 为 'DETID' 的检测器上的车辆数量。支持感应线圈和车道区域检测器。也支持省略检测器 id 的前缀。(见 'z:')
- 'w:DETID':返回 id 为 'DETID' 的检测器上车辆的最长个体等待时间(以秒为单位)。支持感应线圈和车道区域检测器。也支持省略检测器 id 的前缀。(见 'z:')
- 'g:TLSINDEX':返回给定索引的连接当前的绿灯持续时间(以秒为单位)
- 'r:TLSINDEX':返回给定索引的连接当前的红灯持续时间(以秒为单位)
- 'p:TLSINDEX':返回在等待区域并打算通过给定 tls 连接索引的人行横道的人员数量
- 'c:': 返回当前周期内的时间
- 用户定义的函数 FNAME:arg1,args2,...,argN,其中 arg 可以是任何不包含空格的表达式(括号内除外)
- 预定义表达式 的符号名称
- 特殊关键字
DEFAULT。如果当前相位的所有检测器都超过了配置的 max-gap,则该关键字将评估为 true。它可以用来轻松地将自定义规则与默认切换行为混合使用。
以下约束适用于表达式:
- 表达式的所有元素必须用空格字符 (' ') 分隔,但运算符 '!'(逻辑否定)除外,它必须紧贴其操作数,中间没有空格。
注意
比较符 '<' 和 '<=' 也受支持,但必须写为 xml 实体 < 和 <=。
命名表达式#
为了组织表达式,可以使用 <condition> 元素作为 <tlLogic> 的子元素来定义命名表达式,这些表达式可以在其他表达式中引用:
<tlLogic id="example" type="actuated" ...>
<condition id="C3" value="z:det5 > 5"/>
<condition id="C4" value="C3 and z:det6 < 2"/>
<condition id="C5" value="g:3 > 20"/>
...
- id 必须是不含空格和 ':' 字符的字母数字字符串。
- value 可以是任何允许用于 'earlyTarget' 或 'finalTarget' 的表达式。
条件值可以在仿真运行时进行可视化。默认情况下,如果相应的可视化选项处于活动状态,则列出所有条件。如果定义了许多条件,则在跟踪器窗口中仅列出一个子集可能很有用。为此,可以 使用以下 <param> 定义之一作为 <tlLogic> 的子元素:
<param key="show-conditions" value="C1 C4"/>:仅显示列出的 id 的条件。<param key="hide-conditions" value="C3 C4"/>:仅显示未列出的条件。
(可见的)命名表达式的值可以选择性地写入 TLS 输出。
示例#
多样化的逻辑条件#
<tlLogic id="example" type="actuated" ...>
<condition id="C3" value="z:Det2.0 > 5"/>
<condition id="C4" value="C3 and z:Det0.0 < 2"/>
<condition id="C5" value="r:0 > 60"/>
<phase ... next="1 2"/>
<phase ... earlyTarget="C3" finalTarget="!C4"/>
<phase ... earlyTarget="(z:D2.0 > 3) and (z:D3.1 <= 4)" finalTarget="C5 or (z:Det3.1 = 0)"/>
</tlLogic>
默认间隔控制逻辑#
使用自定义条件复制的默认间隔控制逻辑。包括网络和检测器定义的完整场景可以在此处下载:
<tlLogic id="C" type="actuated" programID="P1" offset="0">
<phase duration="33" state="GgrrGgrr" minDur="5" maxDur="60" />
<phase duration="3" state="ygrrygrr" earlyTarget="NS"/>
<phase duration="6" state="rGrrrGrr" minDur="5" maxDur="60" />
<phase duration="3" state="ryrrryrr" earlyTarget="NSL"/>
<phase duration="33" state="rrGgrrGg" minDur="5" maxDur="60" />
<phase duration="3" state="rrygrryg" earlyTarget="EW"/>
<phase duration="6" state="rrrGrrrG" minDur="5" maxDur="60" />
<phase duration="3" state="rrryrrry" earlyTarget="EWL"/>
<condition id="NS" value="z:D0.0 > 3 and z:D2.0 > 3"/>
<condition id="NSL" value="z:D0.1 > 3 and z:D2.1 > 3"/>
<condition id="EW" value="z:D1.0 > 3 and z:D3.0 > 3"/>
<condition id="EWL" value="z:D1.1 > 3 and z:D3.1 > 3"/>
</tlLogic>
注意
表达式 'z:D0.0' 检索检测器 'C_PI_D0.0' 的检测间隔,但前缀 'C_PI_' 可以省略。
默认间隔控制逻辑,可以跳过左转相位#
<tlLogic id="C" type="actuated" programID="P1" offset="0">
<phase duration="33" state="GgrrGgrr" minDur="5" maxDur="60" next="1 8"/>
<phase duration="3" state="ygrrygrr" earlyTarget="NS"/>
<phase duration="6" state="rGrrrGrr" minDur="5" maxDur="60" />
<phase duration="3" state="ryrrryrr" earlyTarget="NSL"/>
<phase duration="33" state="rrGgrrGg" minDur="5" maxDur="60" next="5 9"/>
<phase duration="3" state="rrygrryg" earlyTarget="EW"/>
<phase duration="6" state="rrrGrrrG" minDur="5" maxDur="60" />
<phase duration="3" state="rrryrrry" earlyTarget="EWL" next="0"/>
<phase duration="3" state="yyrryyrr" earlyTarget="NS and NSL" next="4"/>
<phase duration="3" state="rryyrryy" earlyTarget="EW and EWL"/>
<condition id="NS" value="z:D0.0 > 3 and z:D2.0 > 3"/>
<condition id="NSL" value="z:D0.1 > 3 and z:D2.1 > 3"/>
<condition id="EW" value="z:D1.0 > 3 and z:D3.0 > 3"/>
<condition id="EWL" value="z:D1.1 > 3 and z:D3.1 > 3"/>
</tlLogic>
公交优先#
<!-- 仅检测公交车 -->
<inductionLoop id="dBus" lane="SC_0" pos="-90" vTypes="busType" file="NUL"/>
<tlLogic id="C" type="actuated" programID="P1" offset="0">
<phase duration="33" state="GgrrGgrr" minDur="5" maxDur="60" />
<phase duration="3" state="ygrrygrr"/>
<phase duration="6" state="rGrrrGrr" minDur="5" maxDur="60" />
<phase duration="3" state="ryrrryrr"/>
<phase duration="33" state="rrGgrrGg" minDur="5" maxDur="60" />
<phase duration="3" state="rrygrryg" earlyTarget="EW or NSbus"/>
<phase duration="6" state="rrrGrrrG" minDur="5" maxDur="60" />
<phase duration="3" state="rrryrrry"/>
<!-- 默认切换规则(根据观察到的间隔延长相位) -->
<condition id="EW" value="z:D1.0 > 3 and z:D3.0 > 3"/>
<!-- 来自南方的公交车优先 -->
<condition id="NSbus" value="3 > z:dBus"/>
</tlLogic>
用表达式覆盖相位属性#
默认情况下,相位属性 'minDur'、'maxDur'、'earliestEnd' 和 'latestEnd' 是以数字方式定义的(或留空)。 可能需要用表达式(即条件 id 或条件值)重新定义这些属性,原因如下:
- 如果这些值可以在信号操作期间动态更改,则切换逻辑可以表达得更简洁。
- 相位定义应可重用于多个控制方案,并且所有可变性都应在常量表中表达(通过
<conditions>定义)。
要覆盖这些属性,它们在 <phase> 中的值必须定义为 -1。对于每个相位和属性,必须定义一个相应的条件,其 id = <ATTRNAME>:<PHASEINDEX>,如下例所示:
<tlLogic id="C" type="actuated" programID="P1" offset="0">
<phase duration="33" state="GgrrGgrr" minDur="10" maxDur="65" name="NS"/>
<phase duration="3" state="ygrrygrr" earlyTarget="NS"/>
<phase duration="6" state="rGrrrGrr" minDur="10" maxDur="65" name="NSL"/>
<phase duration="3" state="ryrrryrr" earlyTarget="NSL"/>
<phase duration="33" state="rrGgrrGg" minDur="-1" maxDur="-1" name="EW" earliestEnd="-1" latestEnd="-1"/>
<phase duration="3" state="rrygrryg" earlyTarget="EW"/>
<phase duration="6" state="rrrGrrrG" minDur="10" maxDur="65" name="EWL"/>
<phase duration="3" state="rrryrrry" earlyTarget="EWL"/>
<condition id="minDur:4" value="10"/>
<condition id="maxDur:4" value="65"/>
<condition id="earliestEnd:4" value="60"/>
<condition id="latestEnd:4" value="80"/>
</tlLogic>
存储和修改自定义数据#
上面描述的 <condition> 元素可用于定义复杂的表达式以及控制程序操作的数值常量。
有时存储和修改在连续的控制逻辑调用之间持续存在的数值可能很有用。为此,可以使用 <assignment> 元素作为 <tlLogic> 的子元素,来定义对命名表达式的条件赋值:
<tlLogic id="example" type="actuated" ...>
<condition id="NS" value="0"/>
<condition id="nSw" value="0"/>
<assignment id="nSw" check="1" value="nSw + 1"/>
<assignment id="NS" check="1" value="0"/>
<assignment id="NS" check="z:D0.0 > 3 and z:D2.0 > 3" value="1"/>
...
</tlLogic>
- id 可以是任何字母数字 id。
- check 可以是任何允许用于条件值的表达式。
- value 可以是任何允许用于条件值的表达式。
每次执行控制逻辑时,所有 assignment 都按定义的顺序执行:如果 'check'-表达式评估为 true(非 0 值),则评估 'value'-表达式,并将结果存储在给定的 id 下:
- 如果 id 是条件元素的 id,则该条件的值将替换为结果的字符串表示(此表示的精度受仿真选项 --precision 限制)。
- 如果 id 不是条件元素的 id,则会在当前作用域中创建/更新一个具有该 id 的双精度值变量。如果赋值不是用户定义函数的一部分,则这是全局作用域。
测试用例 find_primes 在交通信号灯控制器内部计算 100 以下的所有质数,作为能力演示。
自定义函数定义#
自定义函数是一种允许使用自定义参数执行多个赋值的机制。
它们使用 <function> 元素在 <tlLogic> 内定义,如下所示:
<tlLogic id="example" type="actuated" ...>
<function id="FNAME" nArgs="2">
<assignment id="COND1" check="1" value="$1 + $2"/>
<assignment id="$0" check="1" value="COND1 * COND1"/>
</function>
<condition id="COND2" value="FNAME:3,4"/>
...
</tlLogic>
- id 可以是任何字母数字字符串。
- nArgs 是函数所需的参数数量。
- $0 是函数返回的值。
- $1 ... $n 是函数参数的值,按它们在 : 之后提供的顺序排列。
- 当评估函数时,所有赋值都按定义顺序进行评估。
- 函数不能赋值给任何已定义的
<condition>id。 - 赋值是函数局部的。
- 函数调用的形式为 id:arg_1,arg_2,...arg_n,参数和逗号之间不能有空格(括号内除外)。
- 函数在调用作用域内进行评估(函数分配的 id 在嵌套函数调用中可访问,但赋值不会传播回调用者)。
在上面的例子中,COND2 接收到的值为 49。
类型 'delay_based'#
与基于车辆之间时间间隔的控制类似,相位延长也可以由存在具有时间损失的车辆触发。具有这种感应类型的 TLS 可以如下定义:
<tlLogic id="0" programID="my_program" offset="0" type="delay_based">
<param key="detectorRange" value="100" />
<param key="minTimeLoss" value="1" />
<param key="file" value="NULL"/>
<param key="freq" value="300"/>
<param key="show-detectors" value="false"/>
<param key="extendMaxDur" value="false"/>
<phase duration="31" minDur="5" maxDur="45" state="GGggrrrrGGggrrrr"/>
...
</tlLogic>
这里,detectorRange 指定了从停车线开始向上游的检测范围(以米为单位)。默认情况下(如果参数未定义),底层的 E2 检测器 被假定为完全覆盖第一个接近的车道。车辆的时间损失在进入检测范围时开始累积。如果其累积时间损失超过 minTimeLoss 的值(当前默认为一秒),则在相应绿灯相位处于活动状态时请求延长该相位。车辆的瞬时时间损失定义为 1 - v/v_max,其中 v 是其当前速度,v_max 是允许的最大速度。详见 [Oertel, Robert, and Peter Wagner. "Delay-time actuated traffic signal control for an isolated intersection." Transportation Research Board 2011 (90th Annual Meeting). 2011.]。
参数#
可以使用几个可选参数来控制 delay_based 交通信号灯的行为。上一节中的示例值是这些参数的默认值,其含义如下:
- detector-range:从停车线开始向上游的检测范围(以米为单位)。
- minTimeLoss:触发相位延长的车辆最小时间损失(以秒为单位)。
- extendMaxDur:在其他方向没有交通的情况下,相位是否可以延长超过
maxDur(在 1.16.0 之前这是默认行为)。 - show-detectors 控制生成的检测器在 sumo-gui 中是可见还是隐藏。也可以通过在 GUI 中右键单击交通信号灯来切换此值。
- 参数 vTypes, file 和 freq 与常规车道区域检测器具有相同的含义。
自定义检测器#
要使用自定义检测器(例如用于自定义放置或输出),可以定义附加参数,其中 KEY 是进入交通信号灯的车道,VALUE 是用户定义的 laneAreaDetector。
<param key="gneE42_2" value="customDetector1"/>
注意
自定义检测器仅在 'tlLogic' 从附加文件加载时才有效。
类型 'NEMA'#
从版本 1.11.0 开始,SUMO 支持根据 'National Electrical Manufacturers Association' 的命名约定和控制逻辑定义控制器,该协会在美国普遍使用。 详细文档见 NEMA。
自定义检测器#
要使用自定义检测器(例如用于自定义放置或输出),可以定义附加参数,其中 KEY 是进入交通信号灯的车道,VALUE 是用户定义的 laneAreaDetector。
<param key="gneE42_2" value="customDetector1"/>
注意
自定义检测器仅在 'tlLogic' 从附加文件加载时才有效。
检测器激活状态(对于默认和自定义检测器)可以选择性地写入 TLS 输出。
加载新的控制方案#
在如上定义了 tls 控制方案后,它可以作为 additional-file 加载;当然,一个 additional-file 可以包含多个控制方案。可以为单个 tls 加载多个控制方案到仿真中。将使用最后加载的控制方案(除非使用 WAUT 描述进行了不同的定义)。如果多个控制方案描述同一个 tls,则所有附加控制方案的子键必须不同。
假设上面定义的控制方案放在一个名为 tls.add.xml 的文件中,它可以在 sumo/sumo-gui 中这样加载:
sumo -a tls.add.xml ...<网络和路径的其他选项>
切换 TLS 'off'#
也可以加载一个将 tls 切换为关闭的控制方案,方法是将 programID 的值设置为 "off"。
<tlLogic id="0" type="static" programID="off"/>
!!! 注意: 'off' 控制方案总是可以从 TraCI 使用。
将所有交通信号灯切换到 'off' 控制方案的另一种方法是设置 sumo 选项 --tls.all-off。
'off' 时的默认行为#
一旦交通信号灯被关闭,它的灯将变为 O(关闭,无信号)和 o(关闭,闪烁)的值,并且它将表现得像一个优先级路口。状态为 O 的连接(链接)将拥有优先权,而状态为 o 的连接将让行。
配置关闭状态下优先方向的规则与没有交通信号灯的路口相同。
'off' 时的全向停车#
通过在构建/编辑网络文件时设置路口(节点)属性 rightOfWay="allwayStop",关闭时的行为将对应于路口类型 allway_stop。
注意
具有 tlType="NEMA" 的交通信号灯在关闭时默认为 allwayStop 行为。要更改此设置,可以使用属性 rightOfWay="mixedPriority"。
用于导入 TLS 控制方案的工具#
来自真实世界交通信号灯系统的描述通常不是以 SUMO-交通信号灯描述的形式到达的。表示上的主要差异在于,SUMO 在任何受控信号改变其状态时定义一个新的 <phase>,而交通工程师区分相位和相位过渡。
为了比手动编辑 XML 更容易地导入,<SUMO_HOME>/tools/tls 中存在一些工具。
- tls_csv2SUMO.py:此工具简化了描述,因为它允许为每个受控的边到边连接定义相位的持续时间。由于其他信号发生变化而拆分为更小的 SUMO 相位是自动完成的。
- tls_csvSignalGroups.py:此工具进一步简化了描述,因为它允许为每个信号组定义绿灯相位的开始和结束时间(最多 2 个绿灯相位),过渡(黄灯、红黄灯)会自动添加。拆分为更小的 SUMO 相位也是自动完成的。
或者,可以使用 netedit 通过图形用户界面编辑控制方案。
修改现有的 TLS 控制方案#
要修改交通信号灯的控制方案,通常需要加载新的控制方案。但是,在仅修改偏移量的特殊情况下,也可以为现有的交通信号灯 id 和 programID 指定新的偏移量:
<additional>
<tlLogic id="0" programID="0" offset="42"/>
</additional>
使用同一个控制器控制多个路口#
在 SUMO 中,一个交通信号灯控制器可以同时控制任意数量的路口。这可以通过以下方法之一实现:
- 在使用 netconvert 构建网络时,在一组节点的 .nod.xml 文件中定义相同的 tl 属性(控制器 ID)。
- 在 netedit 中为多个节点设置相同的 tl 属性。
- 在使用 netconvert 构建网络时设置选项 --tls.join。这将自动连接默认距离 20m 内(可通过设置选项 tls.join-dist <FLOAT> 自定义)的节点的交通信号灯。
请注意,在这种情况下,每个相位的状态向量将与受控交叉口的总数一样长。此外,连接的 tls 索引将不同于连接索引(因为后者从每个交叉口的 0 开始,而 tls 索引在控制器内是唯一的)。
注意
生成的 TLS 程序将尝试识别主要方向,但通常需要一些手动校正。
定义信号组#
在 SUMO 中,受控交叉口的每个车道到车道连接都被分配一个称为 link tls index 的索引。该索引用于通过在状态向量中查找该索引处的字符代码来确定每个相位的状态。连接索引可以在 sumo-gui 中通过设置路口可视化选项 show link tls index 来显示。默认情况下,连接索引对于每个连接是唯一的,并按顺时针方式分配,从北方开始(与用于定义通行权规则的路口连接索引相同)。当定义联合 TLS 时,索引按照受控路口的顺序继续其编号。
每个连接的 tls 索引可以在 .tll.file 中自由分配,或通过在 netedit 中设置属性 linkIndex。通过为多个连接分配相同的索引,它们形成一个信号组,并始终显示相同的状态(因为它们引用相同的状态索引)。这允许缩短并因此简化状态向量。
自动创建信号组#
netconvert 支持通过设置选项 --tls.group-signals 来自动定义信号组。要用连接到索引的 1 对 1 分配替换现有的信号组,可以使用选项 --tls.ungroup-signals。
netedit 也支持在交通信号灯模式框架中使用 'Group Signals' 和 'Ungroup Signals' 功能来创建和移除信号组。
定义控制方案切换时间和程序#
在实践中, tls 通常在一天中使用不同的控制方案,也可能在工作日和周末使用不同的控制方案。可以使用 WAUT("Wochenschaltautomatik" 的缩写,意为每周开关自动装置)加载控制方案之间切换时间的定义。
假设一个 tls 知道四个控制方案——两个用于工作日,两个用于周末,其中从 22:00 到 6:00 使用夜间计划,从 6:00 到 22:00 使用日间计划,并且已经定义了名为 "weekday_night"、"weekday_day"、"weekend_night"、"weekend_day" 的控制方案。为了描述切换过程,我们必须首先描述切换,假设我们的仿真从星期一 0.00(秒 0)运行到下一个星期一 0.00(秒 604800):
<WAUT refTime="0" id="myWAUT" startProg="weekday_night">
<wautSwitch time="21600" to="weekday_day"/> <!-- 星期一, 6.00 -->
<wautSwitch time="79200" to="weekday_night"/> <!-- 星期一, 22.00 -->
<wautSwitch time="108000" to="weekday_day"/> <!-- 星期二, 6.00 -->
... 更多工作日 ...
<wautSwitch time="453600" to="weekend_day"/> <!-- 星期六, 6.00 -->
... 周末 ...
</WAUT>
WAUT 中的字段含义如下:
| 属性名称 | 值类型 | 描述 |
|---|---|---|
| id | 字符串 id | 定义的 WAUT 的名称 |
| startProg | 字符串 id | 仿真开始时将使用的控制方案 |
| refTime | 时间 | 一个参考时间,用作后续给定切换时间的偏移量(以仿真秒或 D:H:M:S 为单位) |
| period | 时间 | 重复切换时间的周期。当设置为 <= 0 时禁用,默认为 0 |
以及 wautSwitch 中的字段:
| 属性名称 | 值类型 | 描述 |
|---|---|---|
| time | int | 切换将发生的时间 |
| to | 字符串 id | 分配的 tls 将切换到的控制方案的名称 |
当然,在读取此定义之前,必须定义具有所用名称的控制方案。此外,切换步骤必须按其执行时间排序。
此外,必须给出关于哪个 tls 将由 WAUT 切换的定义,如下所示:
<wautJunction wautID="myWAUT" junctionID="RCAS" [procedure="Stretch"] [synchron="t"]/>
这里,属性的含义如下:
| 属性名称 | 值类型 | 描述 |
|---|---|---|
| wautID | 字符串 id | tls 应由其切换的 WAUT 的 id |
| junctionID | 字符串 id | 要分配给 WAUT 的 tls 的名称 |
| procedure | 字符串枚举 | 要使用的切换算法("GSP" 或 "Stretch")。如果未设置,控制方案将立即切换(默认) |
| synchron | bool | 额外信息,指示切换是否应同步进行(默认:false) |
可以将多个 tls 分配给单个 WAUT。理论上,也可以将多个 WAUT 分配给单个路口,但这在现实中不会这样做。
additional-file 中的完整定义如下所示。它将触发交通信号灯逻辑 X 在控制方案 S1 和 S2 之间切换,初始控制方案名为 0。
<additional>
<tlLogic id="X" type="static" programID="S1" offset="0">
<phase duration="50" state="Gr"/>
<phase duration="50" state="rG"/>
</tlLogic>
<tlLogic id="X" type="static" programID="S2" offset="0">
<phase duration="30" state="Gr"/>
<phase duration="80" state="rG"/>
</tlLogic>
<WAUT startProg="0" refTime="100" id="w1">
<wautSwitch to="S1" time="300"></wautSwitch>
<wautSwitch to="SS" time="800"></wautSwitch>
</WAUT>
<wautJunction junctionID="X" wautID="w1"></wautJunction>
<additional>
注意
如果加载了一个名为 "online" 的交通信号灯控制方案,该控制方案将中断该交通信号灯的 WAUT 切换。这可用于通过 TraCI 覆盖 WAUT 行为。
交通信号灯性能评估#
用于自动生成检测器的工具#
一些工具可用于帮助生成用于评估交通信号灯的检测器定义。所有工具都位于 <SUMO_HOME>/tools/output。
注意
感应式交通信号灯不需要添加检测器定义,因为它们会为内部使用生成自己的检测器。
- generateTLSE2Detectors.py 生成一个包含区域检测器的文件。所有进入交叉口的车道都被这些检测器覆盖。距离交叉口的偏移量可以使用选项 --distance-to-TLS <FLOAT>(或 -d <FLOAT>)给出,默认为 .1m。生成的检测器要么在给定长度后结束,使用 --detector-length <FLOAT>(或 -l <FLOAT>)定义(默认为 250m),要么在车道末端结束(如果车道短于此长度)。
- generateTLSE3Detectors.py 生成一个包含多入口/多出口检测器的文件。为进入交通信号灯的每条边构建检测器。这些边的所有车道都被出口点覆盖。这些点距离交叉口的偏移量可以使用选项 --distance-to-TLS <FLOAT>(或 -d <FLOAT>)给出,默认为 .1m。进入边向上游追溯,直到给定的长度(使用 --detector-length <FLOAT>(或 -l <FLOAT>)定义,默认为 250m),或到达另一个交通信号灯,或不存在更上游的边。入口点在这些点生成。
在这两种情况下,必须使用选项 --net-file <FILE>(或 -n <FILE>)给出网络。要生成的包含检测器定义的文件可以使用选项 --output <FILE>(或 -o <FILE>)给出,默认为区域检测器的 "e2.add.xml",以及多入口/多出口检测器的 "e3.add.xml"。默认情况下,由 generateTLSE2Detectors.py 生成的区域检测器将其度量写入 "e2output.xml",由 generateTLSE2Detectors.py 生成的多入口/多出口检测器写入 "e3output.xml"。可以使用选项 --results-file <FILE>(或 -r <FILE>)更改输出文件名。生成报告的频率默认为 60 秒。可以使用选项 --frequency <INT>(或 -f <INT>)进行更改。
通过 TraCI 控制交通信号灯#
TraCI 提供了各种控制交通信号灯的函数。基本方法概述如下
设置相位#
通过 TraCI 实现自适应控制的常见模式是加载一个控制方案(通常来自附加文件),其中所有绿灯相位都有较长的持续时间(例如 1000 秒),以避免 SUMO 进行切换,然后在绿灯相位应该结束时使用 setPhase 函数切换到下一个相位(通常是黄灯相位)。这种方法的好处是,黄灯相位和全红相位仍然可以由 SUMO 自动处理,控制脚本只需确定当前绿灯相位的持续时间。
要实现具有分支相位过渡的控制器,请提供多个到后续绿灯相位的过渡,并在调用 setPhase 时,选择启动到目标绿灯相位过渡的黄灯相位。
这些额外的过渡相位可以添加到控制方案的末尾,并且可选的相位属性 "next" 可用于指示过渡结束后下一个相位。
有关以此方式控制交通信号灯的教程,请参见 Tutorials#TraCI_Tutorials。
设置持续时间#
使用函数 setPhaseDuration,可以修改当前相位的剩余持续时间。请注意,当在下一个相位周期中再次遇到同一相位时,这不会生效。
设置状态#
控制交通信号灯的另一种方法是使用函数 setRedYellowGreenState 直接设置所有连接的信号状态。使用此函数后,SUMO 将不再修改状态(直到使用 setProgram 切换到另一个控制方案)。因此,脚本必须处理所有相位和过渡。
设置完整的控制方案#
使用方法 setProgramLogic,可以加载静态信号计划。由于此方法需要复杂的数据结构作为参数,建议首先使用 getAllProgramLogics 获取数据结构,然后进行修改。
在预定义的控制方案之间切换#
SUMO 可以从 .net.mxl 文件和附加文件加载多个交通信号灯控制方案。使用 TraCI 函数 setProgram,脚本可以在它们之间切换。
信号计划可视化#
在 sumo-gui 中,右键单击交通信号灯允许打开一个包含 'Show Phases' 和 'Track Phases' 项的菜单。这些项打开新的窗口,如下所述。
Show Phases#
这显示了所有受控连接在完整定义相位列表中的信号状态。这里,时间在 x 轴上,每个连接索引有一行。底部的 x 轴显示从 0 开始的每个相位变化的时间。
时间可以在以下样式之间切换: - Seconds:以秒为单位的绝对仿真时间。 - MM::SS:当前分钟和秒(值每小时重复一次)。 - Time in Cycle:交通信号灯周期内的当前秒数(在开始相位 0 时或在某些与绝对仿真时间对齐时重置)。
可选地,可以为每个相位写入绿灯相位持续时间。顶行包含相位索引,但可以更改为显示相位名称。(相位名称是可选的,为了简洁,只显示 'Green' 相位的名称)

注意
所有相位都将按定义顺序显示。如果使用了相位属性 'next',这可能与它们的操作顺序不同。
Track Phases#
这显示了过去 X 秒操作中所有受控连接的信号状态演变(通过 'Range' 值设置)。基本布局与 'Show Phases' 窗口相同。
可以通过复选框激活以下附加功能:
- detector:显示所有控制此交通信号灯的检测器的激活状态。
- conditions:显示为此交通信号灯定义的条件的布尔值。当条件的数值不同于零时,将绘制一个彩色块。
注意
当鼠标悬停在活动条件块上时,将显示条件的数值。

