从 .CSV 格式的 AVL (GPS) 数据创建伪 GTFS 数据集

Create a pseudo GTFS dataset from AVL (GPS) data in .CSV format

我有一个城市 public 交通系统的 .csv 格式的自动车辆定位 (AVL) 数据集。我想使用这个 AVL 数据集构建一个 GTFS dataset 用于 运行 可访问性分析。

我看到了如何根据 SQL database(here) 中存储的 GPS 数据创建 GTFS 数据集的解决方案,但是当 GPS 数据是以 .csv 格式存储,这里就是这种情况。我很乐意对此提供任何帮助,但如果解决方案出现在 RPython.

中,我会很高兴

我已经有了 GTFS 的 stops.txt 文件,但我想我需要创建文件 shapes.txttips.txtroutes.txtstop_times.txt.

这是我的 GPS.csv 数据集的样子:

             timestamp  order  line      lat      long      speed route_name
1: 2016-02-24 00:04:56 B27084   905    -22.9     -43.3      32.00   12860326
2: 2016-02-24 00:05:07 B41878  2302    -22.9     -43.2       0.19   12860386
3: 2016-02-24 00:04:37 B75563   928    -22.9     -43.2       0.00   12867184
4: 2016-02-24 00:05:17 D86084   852    -23.0     -43.6      24.26   12860043
5: 2016-02-24 00:04:58 C41420          -22.9     -43.2       0.00         NA
6: 2016-02-24 00:04:47 C30084          -23.0     -43.3       0.00         NA

需要五个文件:agency.txtroutes.txttrips.txtstop_times.txtstops.txt。对于仅用于计算可访问性目的的 pseudo-GTFS,可以省略必需文件中的许多可选字段,以及所有可选文件。然而,您可能想要复制真实的或构建它们,因为它们对此很有用(例如,人们在选择旅行方式时会考虑票价,因此您可以使用 fares.txt)。

仔细阅读specification

agency

如果可以接受table所有路线都由同一机构提供服务,那么您的路线可以简单地是:

agency_id,agency_name,agency_url,agency_timezone,agency_lang,agency_phone
XXX,My Awesome Agency,http://example.com,,,

即您只需要前三个字段。

agency.txt意在表示:

One or more transit agencies that provide the data in this feed.

routes

你需要:

  • route_id(主键)
  • route_short_name
  • route_long_name
  • route_type(必须在 0–7 范围内;表示模式)

示例:

route_id,agency_id,route_short_name,route_long_name,route_desc,route_type,route_url,route_color
12860326,XXX,12860326,12860326,,3,,
12860386,XXX,12860386,12860386,,3,,
12867184,XXX,12867184,12867184,,3,,

我不知道如何处理示例数据中没有分配给它们的路线的路线。我也不知道 order 指的是什么。也许 order 是路线的名称?只要你能想出与 "route" 标识符概念相同的东西,你就可以使用它。作为参考,"route" 定义为:

A route is a group of trips that are displayed to riders as a single service.

trips

A trip is a sequence of two or more stops that occurs at specific time.

你需要:

  • trip_id(主键)
  • route_id(外键)
  • service_id(外键)

示例:

route_id,service_id,trip_id,trip_headsign,direction_id,block_id,shape_id
12860326,1,1,,1,,12860326
12860326,1,2,,1,,12860326
12860386,1,1,,1,,12860386
12860386,1,2,,2,,12860386

direction_id,虽然是可选的,但往往非常有用,尽管它是可选状态,但我有几个摄取 GTFS 的应用程序需要它。

service_id 很棘手,并且与日历日期结合使用。它允许 GTFS 轻松表示 "normal" 工作日服务,以及假期在工作日时的假期服务。出于您的目的,您可能只对所有内容使用 1,但这取决于您的应用程序以及何时收集您的 AVL 数据。当我处理类似的应用程序时,我在我的数据库中维护了一个查找 table,它告诉我某个特定日期是 public 假期,and/or 学校假期,and/or在大学学期期间,因为巴士路线改变以适合学生。

shape_id 是可选的,但如果您想在地图上绘制路线或使用 OpenTripPlanner 等工具,这将是至关重要的。

stop_times

Times that a vehicle arrives at and departs from individual stops for each trip.

您将需要:

  • stop_id(主键)
  • trip_id(外键)
  • arrival_time
  • departure_time
  • stop_sequence

编写脚本时这将需要最多的工作。它将比所有其他文件的总和大几个数量级。

stop_idtrip_id 很高兴与已经确定的停靠点和行程相关。 departure_timearrival_time 将在 AVL 数据的 两行 中,在许多情况下,实际识别服务何时到达停止是最困难的方面这个任务。访问乘客智能卡数据会更容易,当服务实际停止时,您可能会发现 AVL 记录的空间集群,因为车辆在特定时间段内不会移动。但是,如果车站空无一人且没有人想下车,则很难确定服务何时 "arrived" 真正到达车站---特别是因为 driver 的行为有时会发生变化,如果他们不打算在预定的时间停下来(例如,如果他们看到没有人在等,他们会走得更快或走捷径)。在您的情况下,speed 值可能会有所帮助,但请注意不要将乘客停靠站与十字路口混淆。

stop_sequence 是可选的,但是应用程序通常期望它存在的另一种情况。无论如何,如果您的脚本无法识别 stop_sequence 那么您可能无法正确创建此文件。

示例:

trip_id,arrival_time,departure_time,stop_id,stop_sequence,stop_headsign,pickup_type,drop_off_type,shape_dist_traveled
1,00:05:07,00:05:54,22018,1,,1,1,0
1,00:07:16,00:08:01,22557,2,,1,1,39
1,00:10:56,00:10:56,22559,3,,1,1,76

指示停留时间是可选的,所以如果这太难计算,arrival_timedeparture_time 可以有效地是同一时刻。

在实践中,pickup_typedrop_off_type 非常有影响力,但通常无法仅从 AVL 数据来确定,除非您的 AVL 收集器真的考虑过在他们的档案中支持 GTFS...不幸的是,可能性很小。您可能只需要始终允许两者,除非您有可以插入的其他信息(例如 "all trips on route 1 after stop 4 in weekday evenings only let passengers off")。

stops

  • stop_id(主键)
  • stop_name
  • stop_lon
  • stop_lat

你说你已经有了这个,太好了。真正的挑战在于通过 stop_id 外键让它与 stop_times 接口。幸运的是,我使用的 AVL 数据识别了服务停止的时间,以及它们停止的位置,使用与时间表的 GTFS 表示中相同的代码。

calendar

要使用 OpenTripPlanner 等工具获得好的结果,您可能需要包含一个 calendar.txt 文件。这也有助于确定 pseudo-GTFS 的有效期,如果您采用的是为定义的时间段建模的方法。例如:

service_id,monday,tuesday,wednesday,thursday,friday,saturday,sunday,start_date,end_date
1,1,1,1,1,1,0,0,20160224,20160226
2,0,0,0,0,0,1,1,20160224,20160226
3,0,0,0,0,0,1,0,20160224,20160226

这表示这些服务的建模周期是从 2016-06-24 到 2016-06-26。在该范围之外请求的任何路线都有未定义的旅行时间。我建议您选择不超过一周的时间段:超过一周,使用 GTFS 的应用程序将开始与数据量作斗争。真正的 GTFS 数据受益于此 "pseudo" 数据无法做到的冗余。

shapes

不用担心shape_dist_traveled,我只是使用虚拟信息(单调递增):它可以从形状推断出来,除非形状过于笼统。

示例:

shape_id,shape_pt_lat,shape_pt_lon,shape_pt_sequence,shape_dist_traveled
12860386,-22.9,-43.3,1,1
12860386,-22.0,-42.9,2,2

备注

总体思路是使用手头的 AVL 数据来满足 specification-meeting 中转提要的最低要求。您可能需要编写自己的脚本来创建这些文件,因为没有针对 AVL 数据的标准。您可以编造一些信息,并且您可能需要这样做:当您尝试使用不完整的提要时,大多数应用程序都会引发异常。事实上,根据我的经验,相当多的应用程序实际上会遇到仅满足最低要求的提要问题,因为程序很差并且大多数 real-world 数据超出了最低标准。

您可能会发现 AVL 数据中的缺陷使其难以使用。最没有table 的情况是 运行 的路由,但 AVL 不起作用。在这种情况下,您的 pseudo-GTFS 将无法准确代表实践中的交通系统。这些几乎不可能被发现。

在这种情况下,我不明白您的 orderlineroute 字段之间的区别。您将需要确定这些最适合的位置;我忽略了它们,因为我不明白它们代表什么。您需要将 AVL 模式与 GTFS 的概念相匹配。

公交系统往往非常复杂,有很多小例外。您最终可能会排除一些特别异常的情况。

您的纬度和经度值看起来不是很精确:如果那是真实数据,您可能无法使用 shapes.txt。尝试要求更精确的车辆位置。