routeSampler.py#
该脚本根据任意组合的转向计数数据、路段计数甚至起讫点(OD)计数数据生成交通(有路径的车辆或流量)。它需要一个定义了可行路径的路径文件作为输入。路径会从输入中(启发式地)采样,以便生成的交通满足计数数据。
路段计数 (edge counts)#
最常用的数据形式是道路(路段)上的交通计数。这些数据可以通过选项 --edgedata-files 以 edgeData 文件 的形式传递给 routeSampler.py。
python tools/routeSampler.py -r <input-route-file> --edgedata-files <edgedata-files> -o <output-file>
只需要路段属性 'id' 和另一个用于交通计数的属性:
<data>
<interval id="arbitrary" begin="0.0" end="300">
<edge id="-58" entered="4"/>
<edge id="45" entered="3"/>
<edge id="-31" entered="15"/>
...
</interval>
...
</data>
用于从 edge-data 文件中读取计数的属性可以通过选项 --edgedata-attribute 设置(默认为 'entered')。
如果您打算针对不同类型的车辆多次调用 routeSamper.py,可以在同一个 <edge> 元素中放入任意数量的计数属性。
Note
默认属性是 'entered',因为该属性与 sumo 生成的 edgeData 文件中的直行交通计数最为对应。
获取计数数据文件#
当使用 routeSampler 作为 dfrouter 或 flowrouter.py 的替代品时,流量输入文件可以使用工具 edgeDataFromFlow.py 转换为 edgeData 文件。
对于较小的场景,通常可以使用 netedit edgeData 模式(在 'Data' 超级模式下) 定义 edgeData 文件。转向文件也可以使用 netedit 的 edgeRelation 模式(同样在 'Data' 超级模式下)创建。
在其他情况下,需要编写自定义代码将计数数据转换为所需格式。
更多 edgeData 文件的来源列在可视化路段相关数据页面上。
转向计数 (turn counts)#
与转向交通相关的交通计数可以按以下格式提供:
转向计数数据必须按以下格式提供:
<data>
<interval id="generated" begin="0.0" end="99.0">
<edgeRelation from="-58.121.42" to="64" count="1"/>
<edgeRelation from="-58.121.42" to="-31" count="3"/>
<edgeRelation from="45" to="-68" count="3"/>
<edgeRelation from="-31.80.00" to="31" count="1"/>
<edgeRelation from="-31.80.00" to="37" count="1"/>
<edgeRelation from="-31.80.00" to="-23" count="13"/>
<edgeRelation from="-92.180.00" to="-60" count="1"/>
</interval>
</data>
示例调用:
python tools/routeSampler.py -r <input-route-file> --turn-files <turn-files> -o <output-file>
用于从转向数据文件中读取计数的属性可以通过选项 --turn-attribute 设置(默认为 'count')。
如果您打算针对不同类型的车辆多次调用 routeSamper.py,可以在同一个 <edgeRelation> 元素中放入任意数量的计数属性。
如果要修改现有场景(即与不同类型的计数数据结合使用),也可以将包含车辆的现有文件转换为转向计数文件。
Note
在环形交叉路口处理转向计数时,进入和离开的路段并不直接相连(因为车辆必须首先通过环形交叉路口内的若干路段)。在这种情况下,必须使用选项 --turn-max-gap,并应将其设置为最大环形交叉路口内的路段数量。
转向比率 (turn ratios)#
与转向交通相关的交通数据也可以以比率的形式按以下格式提供:
<data>
<interval id="generated" begin="0.0" end="99.0">
<edgeRelation from="-58.121.42" to="64" probability="0.3"/>
<edgeRelation from="-58.121.42" to="-31" probability="0.7"/>
<edgeRelation from="-31.80.00" to="31" probability="0.1"/>
<edgeRelation from="-31.80.00" to="37" probability="0.1"/>
<edgeRelation from="-31.80.00" to="-23" probability="0.8"/>
</interval>
</data>
示例调用:
python tools/routeSampler.py -r <input-route-file> --turn-ratio-files <turn-ratio-files> -o <output-file>
用于从转向数据文件中读取比率的属性可以通过选项 --turn-ratio-attribute 设置(默认为 probability)。
如果您打算针对不同类型的车辆多次调用 routeSamper.py,可以在同一个 <edgeRelation> 元素中放入任意数量的计数属性。
Caution
转向比率必须与其他计数数据结合使用,以定义交通的绝对水平。这可以是任何其他计数数据格式,也可以通过设置选项 --total-count 来实现。
获取初始路径#
由 randomTrips.py (--route-output) 生成的路径可以是一个很好的输入源。以下 randomTrips.py 选项可能会有帮助:
- --fringe-factor: 设置一个较高的值将生成大量直行交通,这对于小型网络是合理的
- --min-distance: 限制短路径会增加生成通过多个计数位置的路径的机会
- --speed-exponent, --lanes: 这两个选项都可用于增加在“重要”道路上开始和结束的路径。这与 --fringe-factor 选项结合使用,可以生成许多在主要道路上进出网络的路径。
- --random-routing-factor: 随机干扰路径选择,以便具有相同起点和终点的行程可能使用不同的路径。值必须大于 1。值为 2 可能会使路段上的表观行驶时间改变其空网行驶时间的 100% 到 200%。这确保了生成的路径最多花费“最快”路径的两倍时间。该值对每个车辆都是重新随机化的,因此不存在系统性偏差。
- --edge-type-file: 加载特定于路段类型的概率,用于生成起点和终点
- --marouter: 使用宏观分配计算路径。这些路径考虑了交通状况,因此与默认的 duarouter 输出(空网中的最快路径)相比,提供了更多的多样性。
最真实的路径来自动态用户分配。即使从随机交通需求开始,此类路径也将覆盖网络中更多合理的路径变体。
示例:
python tools/randomTrips.py -n <input-net-file> -r sampleRoutes.rou.xml
python tools/routeSampler.py -r sampleRoutes.rou.xml --edgedata-files <edgedata-files> -o <output-file>
Note
路径文件中的出发时间将被忽略,仅使用 <route> 元素。也可以使用带有命名路径但没有车辆的路径。
广义路径限制 (Generalized route restrictions)#
默认情况下,输入选项 --edgedata-files 和 --turn-files 允许限制单个路段和连续路段对的计数。
要为更长的连续路段序列定义计数限制,可以对 <edgeRelation> 元素使用可选的 'via' 属性:
<edgeRelation from="A" to="D" via="B C" count="42"/>
要为非连续路段定义计数限制,可以使用选项 --turn-max-gap <edgeRelation from="A" to="D" .../> 将应用于包含 "A B"、"A X D" 或 "A X Y D" 的路径,但不适用于 "A X Y Z D"。
起讫点(OD)限制#
以下部分描述的是指路径的起点和终点,而不是某些中间路径路段的计数。 将此类计数与 routeSampler.py 一起使用,允许将它们与其他形式的计数或比率相结合。(这与 od2trips 不同,后者仅导入 OD 计数,不包含其他内容)。
如果加载了起讫点计数,则假定它们提供了场景的完整覆盖。这意味着,如果未给出特定起讫点对的计数,则假定计数为 0,并且不会在相应的路段或 TAZ 之间生成交通。要更改此行为,可以设置选项 --extra-od。在这种情况下,只要不超过加载的计数,就可以生成任何关系之间的交通。
基于路段 (Edge Based)#
当使用选项 --od-files 加载 edgeRelation 文件时,将添加起讫点计数。 这可用于将(基于路段的)OD 关系与其他计数数据相结合。
<edgeRelation from="A" to="D" count="42"/>
上述计数数据示例将匹配从路段 A 开始并在路段 D 结束的路径。
工具 route2OD.py 支持选项 --edge-relations,以将任何类型的路径文件转换为合适的基于路段的起讫点 edgeRelations 文件。
基于交通分区(TAZ)(TAZ (district) Based)#
当使用选项 --taz-files 加载 TAZ 文件 时,可以定义交通分区(TAZ,也称为区)之间的计数。 计数数据本身必须按以下形式提供,并使用选项 --od-files 加载:
<data>
<interval id="generated" begin="0.0" end="99.0">
<tazRelation from="1_2" to="2_0" count="5"/>
</interval>
</data>
由 tazRelation 属性 from 和 to 引用的 TAZ id 必须在加载的 --taz-files 中定义。
上述计数数据示例将匹配从 TAZ 1_2 的任何路段开始并在 TAZ 2_0 的任何路段结束的路径。
出发/到达限制 (Depart / Arrival restrictions)#
可以从 edgeData 文件中读取附加属性,以设置每个路段的出发或到达车辆总数。这可用于在原本没有交通的地方创建交通,也可以通过与其他计数数据(即转向计数)一起作为附加约束来限制采样的路径。可用选项如下:
- --arrival-attribute: 设置用于读取路段上到达车辆数的属性
- --depart-attribute: 设置用于读取路段上出发车辆数的属性
Note
当加载的 edgedata 文件仅包含到达或出发属性时,可以将 --edgedata-attribute 的值设置为 'None',以抑制关于缺少属性的警告。
总计数限制 (Total count restrictions)#
选项 --total-count INT[,INT,..] 可用于指定生成的车辆总数。通常可能出现以下两种情况:
- total-count 高于 通过匹配所有其他给定位置的交通将生成的交通量:在这种情况下,任何不通过计数位置的路径都将用于生成额外的交通(从而避免超过任何特定位置的计数)。用户必须确保此类路径可用。
- total-count 低于 通过匹配所有其他给定位置的交通将生成的交通量:在这种情况下,一旦达到总计数,采样将中止。可以使用选项 --optimize 来改进在总计数约束下匹配所有计数位置的效果。
根据 --total-count 的参数值,适用以下规则:
- 如果 total-count 是一个与数据间隔数量相匹配的整数值列表,则每个数据间隔将使用输入列表中的相应计数值
- 如果 total-count 是单个整数值且存在多个数据间隔,则给定的计数将按每个间隔所有计数位置的总和成比例分配
- 如果 total-count 设置为特殊值
input(--total-count input),则使用输入路径文件中传递的车辆数作为 total-count。如果存在多个数据间隔,则根据出发时间将输入车辆分配给每个间隔。如果设置了选项 --pedestrians,则将计算人员的出发量(无论其计划是否包括步行或乘车)。
输出样式 (Output Styles)#
默认情况下,routeSampler 将生成带有嵌入式路径的个体车辆。这可以通过以下选项进行更改(也可以组合使用):
- --write-route-ids (快捷方式 -I): 写入命名路径,并让车辆通过其 id 引用路径
- --write-route-distribution STR (快捷方式 -u): 将所有路径放入一个路径分布(具有适当的路径概率)中,并让所有车辆引用此分布(模拟计数将因此由于从分布中采样而变化)
- --write-flows number (快捷方式 -f): 写入
<flow>定义而不是车辆。流的精确车辆数将在默认情况下生成的最早和最晚车辆出发时间之间均匀分布 - --write-flows probability: 写入
<flow>定义而不是车辆。流将使用 'probability' 属性定义,因此预期车辆数等于默认情况下将生成的车辆数,但由于采样效应,具体数量会有所不同 - --pedestrians: 写入人员和带有步行的 personFlows,而不是车辆和流
- --prefix: 使用给定字符串作为车辆和路径 ID 的前缀。这需要将多次 routeSampler 运行(即针对不同交通模式)的输出组合到单个模拟中。否则会出现关于重复 ID 的错误。
车辆属性 (Vehicle attributes)#
使用选项 --attributes <STRING>,可以向生成的车辆提供附加参数(注意引号字符的使用)。
python tools/routeSampler.py -n input_net.net.xml -r candidate.rou.xml -o out.rou.xml -d data.xml
--attributes="departLane=\"best\" departSpeed=\"max\" departPos=\"random\""
上述属性将使车辆随机分布在它们的起始路段上,并以高速在合理的车道上插入。
Note
在 Linux 上,行程属性的引号也可以使用以下样式:--attributes 'departLane="best" departSpeed="max" departPos="random"'
多种车辆类型 (Multiple vehicle types)#
为了区分不同类型的车辆,可以使用不同的属性多次运行 routeSampler。注意,还需要设置选项 --prefix 以防止 ID 重复。下面的示例使用两个具有不同计数值(存储在默认属性 'entered' 中)的 edgedata 文件创建由汽车和卡车组成的交通。
python tools/routeSampler.py --attributes="type=\"car\"" --edgedata-files carcounts.xml --prefix c -o cars.rou.xml -r candidate.rou.xml
python tools/routeSampler.py --attributes="type=\"heavy\"" --edgedata-files truckcounts.xml --prefix t -o trucks.rou.xml -r candidate.rou.xml
或者,计数值也可以存储在同一文件的不同属性中(例如 'count1', 'count2'):
python tools/routeSampler.py --attributes="type=\"car\"" --edgedata-files counts.xml --edgedata-attribute count1 --prefix c -o cars.rou.xml -r candidate.rou.xml
python tools/routeSampler.py --attributes="type=\"heavy\"" --edgedata-files counts.xml --edgedata-attribute count2 --prefix t -o trucks.rou.xml -r candidate.rou.xml
运行模拟时,'car' 和 'heavy' 类型(先前设置为车辆属性)必须在附加文件中定义,如下例所示(types.add.xml):
<additional>
<vType id="car"/>
<vType id="heavy" vClass="truck"/>
</additional>
然后可以像这样调用模拟:
sumo -n net.net.xml -a types.add.xml -r cars.rou.xml,trucks.rou.xml
采样 (Sampling)#
在此阶段,路径会在输入计数施加的限制内随机选择。 只有通过至少指定数量计数位置的路径(选项 --min-count,默认为 1)才有资格被采样。
默认采样 (Default Sampling)#
默认情况下,采样将按以下方式迭代执行:
- 选择一个尚未达到其计数且仍有可行路径的随机计数位置
- 选择一条通过此计数位置的随机路径
直到所有计数位置都达到其测量计数,或者没有可行路径(所有通过的计数位置都低于输入计数的路径)为止。
加权采样 (Weighted Sampling)#
通过设置选项 --weighted。采样算法会改变。为每条路径从输入加载一个概率值。概率可以使用路径属性 'probability' 显式指定,也可以在路径输入中多次出现具有相同路段序列的路径时隐式指定。采样将按以下方式迭代执行:
- 按概率采样选择一条随机的可行路径
直到所有计数位置都达到其测量计数,或者没有可行路径(所有通过的计数位置都低于输入计数的路径)为止。
优化 (Optimization)#
默认情况下,将从输入路径集中采样路径,直到无法在不超出任何计数的情况下添加更多路径为止。这可能仍会使某些计数低于其目标值。
选择一个多路径集合以匹配所有计数值的问题可以表述为一个整数线性规划问题 (ILP)。
RouteSampler 通过将其松弛为线性规划问题 (LP) 并将其传递给 LP 求解器库 (scipy) 来计算此 ILP 的近似解。然后将产生的非整数解舍入为整数解。通常需要找到一个接近初始采样解的优化解。这样,输入中包含的路径概率可以在一定程度上得到保留。
通过设置选项 --optimize <INT>。每条路径的使用次数最多可以改变 <INT> 次。这定义了在使用与输入中相同的路径分布和优化计数之间的权衡。
当设置选项 --optimize full 时。对路径分布没有约束,任何路径都可以根据需要多次使用以达到计数。
选项 --minimize-vehicles
Note
优化需要 scipy。
进一步校准 (Further Calibration)#
可以将生成的输出加载到 routeSampler.py 中进行另一轮优化。通过设置选项 --optimize-input,将跳过采样步骤,直接在输入路径集上运行优化器。
通过删除特定路径或添加新路径,用户可以以迭代方式调整生成的交通。
质量控制 (Quality Control)#
导致 routeSampler 结果与用户期望之间出现偏差的原因有很多。本节列出了常见原因,并记录了可用于判断结果质量的输出。
问题区域 (Problem areas)#
- 选择一组路径来匹配给定的计数集通常是一个欠定问题,这意味着没有唯一的解。如果解空间的约束不足(计数不够),所选解可能显得不合理
- 输入路径不能代表真实路径 - 未覆盖计数位置 - 包含不太可能的路径
- 时间模式未被给定的间隔数据捕获(例如,仅拥有全天的计数)
- 交通计数在间隔内不是平稳的(例如,单个车辆通过一系列相距很远的计数位置,每个间隔记录不同的位置)。在这种情况下,覆盖所有计数位置的路径将不会被采样。(在这种情况下必须选择更长的间隔)。
- 计数数据中的不一致性
- 许多短路径(可以通过设置选项 --min-count 来防止)
文本质量指标 (Textual quality metrics)#
- 不足位置 (underflow locations): 所有交通量少于输入中定义的计数位置的统计信息
- 溢出位置 (overflow locations): 所有交通量多于输入中定义的计数位置的统计信息(仅在优化后对小数计数进行舍入时发生)
- GEH 统计: 达到定义的 GEH 阈值的位置的统计信息(可通过选项 --geh-ok 配置,默认为 5)
- 匹配计数的总数和百分比(注意,这与车辆数不同,因为每辆车可能被多次计数)
空间质量数据 (Spatial quality data)#
通过设置选项 --mismatch-output FILE,将创建一个 [edgeData] 文件,其中包含每个时间间隔的输入和输出计数之间的差异(deficit)以及输入计数(measuredCount):
示例:
<data>
<interval id="deficit" begin="0.0" end="99.0">
<edgeRelation from="-58.121.42" to="64" measuredCount="1" deficit="0"/>
<edgeRelation from="-58.121.42" to="-31" measuredCount="3" deficit="0"/>
<edgeRelation from="45" to="-68" measuredCount="3" deficit="1"/>
...
</interval>
</data>
此类数据文件可以在 sumo-gui 中可视化,也可以使用 plot_net_dump.py 绘制。
generateTurnRatios.py#
该脚本用于根据给定的路径文件计算从一个路段到其下游路段的转向比率。输出文件可以直接用作 routeSampler.py 和 jtrrouter 的输入。时间间隔将跨越路径文件的最小和最大出发时间,但也可以使用选项 --begin、--end 和 --interval 进行配置。
python tools/turn-defs/generateTurnRatios.py -r <route-file>
标准输出是交通量(jtrrouter 会自动归一化)。使用选项 -p,转向比率将被写为 [0,1] 范围内的值。
generateTurnDefs.py#
该脚本允许根据允许特定转向的车道数生成转向定义。基本功能是均匀分布交通,即:
- 将进入的交通均匀分布在形成道路的车道上
- 将分配给每条车道的交通量均匀分配到该车道允许转向的目的地。
- 对正在处理的道路允许转向的每个目的地的值求和。
示例用法
python tools/turn-defs/generateTurnDefs.py --connections-file connections.con.xml --turn-definitions-file output.turndefs.xml
该脚本允许通过新的交通分布策略(例如,基于高斯分布)轻松扩展。有关详细信息,请参阅 DestinationWeightCalculator 类。
该脚本处理提供的 *.con.xml 文件中给出的连接。有关使用详情,请使用 --help 选项执行 generateTurnDefs.py 脚本。
Note
您可以使用 netconvert 生成包含网络中所有连接的连接文件 - 参见 --plain-output-prefix 选项。
turnCount2EdgeCount.py#
该脚本将转向计数数据转换为 edgeData。
python tools/turn-defs/turnCount2EdgeCount.py -t <turn-file> -o <output-file>
turnFile2EdgeRelations.py#
该脚本将已弃用的转向文件格式转换为 edgeRelation 格式
python tools/turn-defs/turnFile2EdgeRelations.py -t <turn-file> -o <output-file>
jtcrouter.py#
JunctionTurnCountRouter 根据转向计数数据生成车辆路径。 它通过将转向计数转换为流量和转向比率文件来实现这一点,这些文件适合作为 jtrrouter 的输入。 然后它在后台调用 jtrrouter。
示例调用:
python tools/jtcrouter.py -n <net-file> -t <turn-file> -o <output-file>
将转向计数转换为路径有三种基本样式:
- 流量从网络中的所有转向计数位置开始,但在到达下一个计数位置时结束
- 流量从网络中的所有转向计数位置开始,并在到达下一个计数位置时被扣除 (--discount-sources)
- 流量仅从网络的边缘开始 (--fringe-flows)
转向计数数据格式#
转向计数数据必须按与 routeSampler 相同的格式提供:
<data>
<interval id="generated" begin="0.0" end="99.0">
<edgeRelation from="-58.121.42" to="64" count="1"/>
<edgeRelation from="-58.121.42" to="-31" count="3"/>
<edgeRelation from="45" to="-68" count="3"/>
<edgeRelation from="-31.80.00" to="31" count="1"/>
<edgeRelation from="-31.80.00" to="37" count="1"/>
<edgeRelation from="-31.80.00" to="-23" count="13"/>
<edgeRelation from="-92.180.00" to="-60" count="1"/>
</interval>
</data>
