U-M Blue Buses
Project Leads: Ulysses O'Donnell, Michael Peng
Project Members: Agam Kohli, Andrew Smirnov, Julia Spilkin, Oliver Wu
The University of Michigan encompasses three regions at Ann Arbor: the Ross Athletic Complex, Central Campus, and North Campus. Traveling between these campuses by foot is often not feasible (especially in the winter), so a bus system is in place to transport students and staff between and within them. As students ride the Blue Buses to catch classes and meetings, their time-sensitive activities rely on the bus system's timeliness, so the bus system's reliability is important.
Unfortunately, some routes are not always reliable. Buses may not operate according to the officially published time intervals, and they can get completely full during rush hours, where unlucky passengers at a stop would have to let the full bus leave and wait for the next bus to arrive. The abundance of "Not In Service" buses at the Central Campus Transit Center is a persistent source of frustration for waiting passengers, especially if their wait exceeds the published time interval for their desired route. Complaints about the unreliability of buses are widely visible on Reddit.
With this project, we seek to evaluate the reliability of Blue Buses quantitatively using aggregations of real-time position reports from Logistics, Transportation and Parking (LTP), the campus unit in charge of the bus system. We intend to identify signs of unreliability, visualize them in real time, and publish them for public access and operational feedback to LTP. In the long term, we aim to identify external factors that influence the reliability of the bus system, such as weather, class schedules, and traffic conditions. We hope that our product will help LTP improve its operational strategies in order to make the Blue Buses more timely and reliable for all.
To monitor the bus system and offer live position reports to users, LTP uses BusTime, a software system developed by Clever Devices. Bus tracking apps (both official and third-party) retrieve route specifications and live position reports from the official LTP BusTime server with a documented API. We run a custom script that uses this API to retrieve live position reports for every Blue Bus every minute and stores these reports in a local SQLite database. Over an entire semester, this script gathered a large corpus of data that describes the history of every route execution by every bus, revealing many signs of unreliability that we encountered in person.
Our immediate goal was to interpret these historical position reports and transform them into figures that summarize the bus system's reliability. We achieve this through a canonical ranking of routes based on their performance and several real-time visualizations of key statistics for each route.
Ranking Bus Routes
The only information given by BusTime was a boolean value representing whether or not a bus was on time. There was no other information regarding what constitutes a delay, and we found that many of the delays were near the end of routes where buses tend to take breaks.
Our goal was to infer real values of delay, not just whether or not they happened. “tatripid” is a column that had a unique ID for a given trip, where a trip constitutes an entire southbound or northbound route. These IDs were unique in a given day, but would be reused from day to day. The first step was to group the data for one day, then group the trips based on their tatripid. Extracting the first and last timestamps from each segment of the grouped data gave us the time for a bus to complete their route. This was done for each trip for each day in our dataset, and then averaged for an average time that each route should take. There was some outlier removal based on the route. For example, if Google Maps says a route should take 15 minutes then time differences below a certain threshold, say 7 minutes, and above a certain threshold, say 23 minutes weren’t considered in the average. Thresholds were set for each route manually, so some future work could be done to remove outliers more systematically.
Our visualization extracts each trip length from the past 6-10 hours of the specified date and plots the difference against the average time. An example of our results is shown below.
We infer the crowding situation in every bus using the psgld variable from BusTime, which takes on one of three values: EMPTY, HALF_EMPTY, and FULL. Given a collection of position reports for a particular route within a contiguous time period, we partition these reports into buckets representing each 10-minute interval within that period. In each bucket, we then tabulate the frequencies of each psgld value and graph these frequencies with a stacked, filled line graph. We generate a load factor for each bucket ranging from 0 to 1 based on these frequencies, where 0 represents completely empty and 1 represents completely full. This metric is intended to summarize the level of crowding for a route within a 10-minute interval regardless of the number of buses operating that route. An example of the crowding graph is shown for Bursley-Baits on April 22, 2022:
Schedule Alignment for Bursley Baits Route
Each of these visualizations were made using Plotly Express, and this made for easy transferring to a dynamic dashboard using plotly dash. The only problem is it is incredibly slow and unoptimized due to time constraints. You may visit the dashboard, but embrace for high loading times and visualizations that aren't entirely accurate.
The dashboard shows each graph for six different routes for the previous 6 hours. This makes it easy to see how certain routes are performing. The dashboard also contains a page for all routes, displaying static rankings and visualizations about our data collection. Future work would include optimizing this dashboard and creating a dynamic ranking aspect.
Throughout the semester we aggregated data, extracted metrics, and built visualizations and systems to quantify and visualize bus performance. Using these tools, it is easy to see when and where buses perform poorly, and when they perform well. While our final result is far from a system that LTP could use efficiently, it offers a promising start.
In the future, optimization of our dashboard and further outlier removal would be necessary for a fully functioning and accurate dashboard. We extracted enough 'vitals' to use them to predict on-time performance, so implementing that to help both drivers and riders would be an exciting next step.