我是靠谱客的博主 漂亮发箍,最近开发中收集的这篇文章主要介绍OMNeT++ & SUMO 学习记录(九)SUMO 交通控制接口 TraCI,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

一、TraCI 简介

TraCI 是交通控制接口(Traffic Control Interface)的简称,通过该接口与模拟器进行通信,可以实现对 SUMO 仿真中的实时交通信息获取和控制仿真对象的形为,与外界进行实时性的交互,极大提高了仿真性能。例如,在一个发生交通堵塞的场景中,可以通过 TraCI 接口获取当前车辆的位置和行驶路线信息,可以在线为车辆重新规划路线,调整既定信号灯相位配时等方法缓解交通拥堵。

二、TraCI 的使用

1、配置环境变量

使用 TraCI 首先要为其配置环境变量,SUMO 中的许多工具要求将环境变量 SUMO_HOME 设置为 SUMO 安装的基本目录,包含文件夹bin和tools的目录。使用命令行运行程序,必须配置 Path 变量和SUMO_HOME 变量。

打开环境变量页面,点击 “新建” ,输入变量名 SUMO_HOME ,变量值为 SUMO 的安装路径。
在这里插入图片描述

如果已经有 Path 变量,双击变量值为其添加新的值即可,如果没有,需要新建该变量并为其添加值,变量值为 bin 文件夹的路径。
在这里插入图片描述
至此,环境变量配置完毕。

2、接口编程语言

TraCI 接口目前支持包括 Python, Java, C++,.NET 等多种主流语言,其中 python 语言的功能最为完善,实现相对简单。

在使用 TraCI 前需要将其安装到 Python 的加载路径上,TraCI 位于 SUMO 安装目录下 tools->traci 文件夹中,打开可以看到 TraCI 的一系列功能函数,我们需要将 tools 目录加载到 Python 中。

打开 Python 安装目录,E:pythonLibsite-packages,新建文本文档 traci.txt,在其中输入 tools 目录的位置:E:SUMOtools ,最后将文件后缀改为 .pth 即可。
在这里插入图片描述
可以在命令行中检查 TraCI 是否安装成功
在这里插入图片描述

三、TraCI 命令

TraCI 命令可以调用一系列库函数,实现仿真数据信息的获取和仿真对象的状态修改,极大程度方便了交通场景的构建,是二次开发不可或缺的重要工具。下面简单介绍各 API 的功能:

1、信息获取类

该类接口的主要功能是获取仿真对象的状态信息值,可以作为仿真输出,可以在输出数据基础上进行研究,对仿真进行改进,以达到理想的效果。下面介绍几个常用的 API :

  • 车辆信息获取(Vehicle Value Retrieval ):获取仿真中车辆的状态值,如仿真环境中的车辆数量 、ID 、行驶路线 、定位 、车速等,可满足各种仿真需求。
  • 信号灯信息获取(Traffic Lights Value Retrieval):返回仿真场景中信号灯相关数据,如返回所有的信号灯 ID 、信号灯总数 、信号灯当前相位及其剩余持续时间 、信号灯控制的车道等。需要注意的是,“getNextSwitch(self, tlsID)” 函数获取的值为信号灯切换到下一个状态的绝对时间(从模拟开始算起),要获取当前相位剩余时间,需要用(getNextSwitch()- Simulation.getTime())。

举例说明:为信号灯设置三个不同的相位,分别是 28s 、3s 和 14s ,在 0 ~ 28s 也就是第一个相位的时间内,getNextSwitch()的值恒定为 28 ,在第二个相位的时间内,getNextSwitch()的值恒定为 31(28+3) ,第三个相位 getNextSwitch()值恒定为 45(28+3+14)。这样,假设获取到了第 3s 仿真数据,信号灯剩余时间就是 28 - 3 = 25s 。
在这里插入图片描述

  • 仿真信息获取(Simulation Value Retrieval):获取仿真过程中某个模拟变量的值,如当前仿真时间 、当前路网中车辆数及车辆 ID 、某时段内进入和离开路网的车辆数 、发生碰撞的车辆数及其 ID 等。

2、状态改变类

该类接口的主要功能是控制仿真对象的状态,例如要测试自定义的车辆在不同路况条件下的性能表现,如果需要分析某一变量对车辆的影响,需要修改该变量的值,如信号灯持续时间、周围车辆密度、道路限速限行等,这时候就可以通过该接口来修改某一变量的值,得到前后的对比实验数据,方便下一步分析改进。下面简单介绍几个常用接口功能:

  • 改变信号灯状态(Change Traffic Lights State) :可以设置信号灯的状态,进行相位切换,设置当前相位持续时间等。可以根据路况的不同和场景的需要,控制信号灯的状态,提高通行效率。
  • 改变车辆状态(Change Vehicle State) :实现车辆控制的核心,常用函数的功能描述及实现方法见下表:
车辆状态功能描述python 实现
停车使车辆停在给定的边沿,给定的位置和车道上。车辆将在给定的时间内停止。setStop
变更车道强制将车道更改为具有给定索引的车道;如果成功,将在给定的时间量(以秒为单位)内选择车道。changeLane
更改目的地给定新的目的地道路,重建行车路线changeTarget
速度将车辆的速度设定为给定值,车速要符合当前的速度模型setSpeed
设置路线为车辆设置行驶路线,车辆将沿给定的路线列表依次驶过setRoute

四、仿真实例解析

TraCI 使用基于 TCP 的客户端/服务器体系结构来提供对 SUMO 的访问,SUMO 作为客户端,由于 TraCI 接口支持多种语言,服务器可以是由某种语言编写的脚本,通过该脚本控制仿真运行。下面的例子以 Python 脚本为例,探讨仿真运行过程和原理:

场景描述:在一个十字路口,东西方向有持续车流,南北方向间歇有车辆通过。使用 TraCI 控制信号灯在南北方向没有车辆时保持东西方向绿灯,当检测到南北方向的车辆,控制信号灯切换相位到南北方向绿灯而东西方向红灯。该例程可以在 …doctutorialtraci_tls 中找到,下面代码已经简化和部分功能修改,在控制信号灯的同时打印出检测器检测到车辆信息。

代码如下,功能参考注释:

# 首先需要从 SUMO_HOME/tools 中导入一些实验用到的 python 模块
import os
import sys
import optparse
import random
import time
import traci
from sumolib import checkBinary
# 其次检查 SUMO_HOME 是否在系统环境变量中,这是进行下一步仿真的必要条件
if 'SUMO_HOME' in os.environ:
tools = os.path.join(os.environ['SUMO_HOME'], 'tools')
sys.path.append(tools)
else:
sys.exit("please declare environment variable 'SUMO_HOME'")
# 是否打开 sumo-gui 进行可视化演示
if_show_gui = True
if not if_show_gui:
sumoBinary = checkBinary('sumo')
else:
sumoBinary = checkBinary('sumo-gui')
# 指定 *.sumocfg 文件的位置
sumocfgfile = "E:\SUMO\doc\tutorial\traci_tls\data\cross.sumocfg"
# 接下来是 *.rou 文件的定义函数
def generate_routefile():
random.seed(42)
# 设定种子值,下面使用 random() 生成的随机数是确定的,确保每次生成的 *.rou 文件相同
N = 3600
# 总仿真步数
pWE = 1. / 10
pEW = 1. / 11
pNS = 1. / 30
# 打开文件,“w” 代表将进行写入操作
with open("data/cross.rou.xml", "w") as routes:
print("""<routes>
<vType id="typeWE" accel="0.8" decel="4.5" sigma="0.5" length="5" minGap="2.5" maxSpeed="16.67" guiShape="passenger"/>
<vType id="typeNS" accel="0.8" decel="4.5" sigma="0.5" length="7" minGap="3" maxSpeed="25" guiShape="bus"/>
<route id="right" edges="51o 1i 2o 52i" />
<route id="left" edges="52o 2i 1o 51i" />
<route id="down" edges="54o 4i 3o 53i" />""", file=routes)
vehNr = 0 # 初始时刻车辆数为 0
for i in range(N):
if random.uniform(0, 1) < pWE:
print('
<vehicle id="right_%i" type="typeWE" route="right" depart="%i" />' % (
vehNr, i), file=routes)
vehNr += 1
if random.uniform(0, 1) < pEW:
print('
<vehicle id="left_%i" type="typeWE" route="left" depart="%i" />' % (
vehNr, i), file=routes)
vehNr += 1
if random.uniform(0, 1) < pNS:
print('
<vehicle id="down_%i" type="typeNS" route="down" depart="%i" color="1,0,0"/>' % (
vehNr, i), file=routes)
vehNr += 1
print("</routes>", file=routes)
# 定义主函数,traci 的核心控制逻辑
def run():
step = 0
traci.trafficlight.setPhase("0", 2) # 设置 ID 为 “0” 的信号灯初始相位是 2,该相位下东西方向绿灯
while traci.simulation.getMinExpectedNumber() > 0: # 获取预计仍要离开网络的车辆的最小数量
time.sleep(0.05) # 设置时延为 50ms
traci.simulationStep()
if traci.inductionloop.getVehicleData("0"): # 若 ID 为 “0” 的检测器检测到车辆通过,则打印出车辆的信息
print(traci.inductionloop.getVehicleData("0"))
if traci.trafficlight.getPhase("0") == 2:
if traci.inductionloop.getLastStepVehicleNumber("0") > 0: # 检测到有南北方向的车辆
traci.trafficlight.setPhase("0", 3) # 切换到 3 相位,南北方向绿灯,东西方向红灯
else:
traci.trafficlight.setPhase("0", 2)
step += 1
traci.close()
generate_routefile()
traci.start([sumoBinary, "-c", sumocfgfile]) # 启动 sumo-gui ,加载 *.sumocfg 文件
run()

运行脚本,仿真效果如下:

在这里插入图片描述
该场景简单模拟了拥有高通行优先级的车辆在 TraCI 控制信号灯路口的优先通行权,在真实环境中,这些车辆可以是执行紧急任务的救护车、消防车、警车等,通过实时控制信号灯,节省时间的同时保证通行安全。

注:本文仅涉及 TraCI 的几个常见使用,更多功能详见官方描述文档。

最后

以上就是漂亮发箍为你收集整理的OMNeT++ & SUMO 学习记录(九)SUMO 交通控制接口 TraCI的全部内容,希望文章能够帮你解决OMNeT++ & SUMO 学习记录(九)SUMO 交通控制接口 TraCI所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(49)

评论列表共有 0 条评论

立即
投稿
返回
顶部