Расписание общественного транспорта в MAPS.ME
Всем привет, меня до сих пор зовут Максим и я застрял на Мапс-ми:) Прошло аж два года с момента написания мной статьи про ОТ в Мапс https://habr.com/ru/articles/837058/ и теперь хотелось бы немного рассказать как мы стоим на месте. Опишу начало нашего долгого пути в область предоставления расписания по уже имеющимся у нас в приложении линиям ОТ.
Данные по расписанию мы берем из общедоступных ГТФС фидов и задача по сути состоит в нахождении соответствия между ОСМ-маршрутом и отдельными поездками в терминологии ГТФС. Немножко окунусь в терминологию ГТФС:
- маршрут это то что соответствует всей информации по номеру автобуса
- поездка это фиксированная траектория для заданного номера автобуса.
В ОСМ же маршрут почти всегда - это траектория из А в Б.
Я привык что обычные автобусы у нас ходят всегда одинаково. А вот где-нибудь в Берлине расписание ГТФС оказывается может содержать тридцать вариантов траекторий для одного номера. Это может быть связано как с изменением пути следования, так и с вариациями урезания пути следования в разные моменты времени.
Невозможно в общем случае предоставить расписание на одну общую линию из Осм от всех вариантов расписания из ГТФС при таких вариациях траектории. Почему? Да потому что мы обещаем пользователю что сев на автобус он доедет до конечной - а при урезанном маршруте этого не произойдет, человек выйдет где-то в поле. Поэтому для начала были выработаны критерии для нахождения соответствия ГТФС-ОСМ, они оцениваются и берется средневзвешенное значение баллов. Начнем:
- попадание в квадрат поиска (тут просто да/нет)
- совпадение типа (да/нет)
- совпадение названия
- совпадение длин
- совпадение по направлению (для не-цикличных)
- совпадение по количеству остановок
- совпадение точек остановок
- совпадение по именам.
Для каждого критерия установлено пороговое значение ниже которого мы заканчиваем сравнение.
В целом можно было бы на этом и закончить историю если бы не куча нюансов. Первый я уже упомянул - это урезанные маршруты, они не попадут по критериям. На них нельзя просто забить, их общий вклад может быть 99 процентов. Далее идет проблема неточного совпадения. Неточность не всегда ошибка, в большинстве случаев - это как раз вариация по траектории следования. И тут возникает вопрос того что если мы будем жестко обрубать все поездки которые отклонились - это нам почти полностью срежет расписание в некоторых регионах. Значит надо выработать критерий психологического принятия отклонения. Сначала думал про какое-то число отличающихся остановок, пропорциональное общему количеству, к примеру 10 процентов. Но эта история быстро привела к куче проблемных кейсов: число отклонений приемлемое, но остановки так далеко уходят в сторону что сев на такой - человек уедет совсем не туда. В то же время были варианты когда число отклонений было довольно велико, но они были не критичными так сказать (соседняя улица / пропуск нескольких остановок по ходу движения). Все эти ситуации как раз привели к выработке критерия “психологического принятия” эквивалентности - когда вышеперечисленные критерии дают приемлемое значение мы оцениваем дополнительно количество отклонений пропорционально длине и что они находятся в коридоре искомого маршрута. Тут кстати хочется отметить что само расписание не будет навешивается на остановки по которым не будет примерно-точного совпадения (вдруг через них действительно не едет автобус). Просто мы не выкидываем расписание совсем, а навешиваем его на преобладающе-правильные остановки, так сказать.
Вопрос неточности в соответствии ГТФС-ОСМ пока не решен в полной мере и есть подозрение что в дальнейшем будет движение в сторону коррекции ОСМ маршрутов версиями из ГТФС. Кажется что в случаях умеренных / допустимых отклонений данные из ГТФС будут более актуальны.
Также столкнулся с фактом что фиды могут сильно пересекаться. Не всегда это чисто дублирование. В них могут быть описаны разные периоды действия расписания: в одном идет коррекция движения на месяц, в другом общее годичное расписание. А еще есть разные записи расписаний на разные дни недели. В целом надо упорядочить временные интервалы, выстроить приоритет более коротким на пересечениях и считать записи в рамках одного фида не конфликтующими а взаимно дополняющими.
Интересный момент еще - оценка времени протухания расписания. Вот мы построили расписание для региона, в него попали данные из разных фидов или даже просто для разных автобусов расписания имеют разные сроки. Вот представьте чисто теоретически: автобус с пятиминутным интервалом имеет расписание на месяц, автобус с интервалом в час имеет расписание на год. Когда расписание считать не валидным? Ведь если они оба проходят через одну какую-то остановку, через два месяца приложение покажет ближайшее прибытие через час. Но если автобусы в разных городах - это уже не так фатально, просто один город не будет иметь на остановке расписания… Пока что я сделал медиану по протуханиям. В некоторых случаях правильным решением будет оценка наличия пересечений с разными интервалами по одной остановке. Но это не универсальное решение: если есть просто расписание временного автобуса на месяц - то протухание через месяц становится плохим сценарием для расписания всего региона. Поэтому медиана.
Как-то я сразу углубился в дебри обработки и совсем не рассказал про сам флоу обработки данных. Скачиваем и распаковываем данные из гтфс-фидов, запускаем самописную приложуху которая
- из planet.osm.pbf вытаскивает ОСМ маршруты
- заполняет сетку этими маршрутами
- параллельно для каждого гтфс-фида делает его пред-разбор и
- для каждой поездки оценивает ее схожесть по выше обозначенным критериям
- выгрузка журналов, составление отчета
Сетка + тип транспорта позволяют быстро локализовать группу маршрутов для сравнения, затем иерархия критериев от быстрых к тяжелым.
Уже столько времени прошло что многие технические вопросы стали восприниматься рутиной, сейчас больше бы даже хотелось остановиться на отчете о сравнении. Он как и наш предыдущий отчет по разбору ОТ - полностью публичный. Хочется приносить пользу не только себе но и всему ОСМ сообществу. https://maps-me-pt-report.s3.amazonaws.com/gtfs/index.html

В нем можно увидеть карту распределения фидов, можно увидеть разбивку по фидам. А провалившись в отчет по конкретному фиду можно увидеть разбивку по маршрутам и поездкам. Для каждой поездки можно увидеть оценки по критериям и ссылки на максимально близкий осм-оригинал и на гтфс-осм сравнение на карте. Наверно не хватает только подготовленной структуры для прямой выгрузки недостающего маршрута в осм. Что-то похожее есть у ОрганикМапс и их gtfs-osm-matcher, но там совершенно другой подход: всё сравнение и привязка идет по остановкам (насколько я смог понять), у нас же по маршрутам. Я не видел пока конечного результата привязки у Органиков в приложении, но у нас выбор маршрута а не остановки для привязки является краеугольным решением. Файл расписаний не содержит ни траекторий ни названий, только привязка к ОСМ-ным айдишникам остановки и линии, это позволило расписание на Берлин затолкать в 10МБ (самый жирный регион согласно отчету, но еще будет расти потому что только 40% ГТФС данных нашли соответствия)
На карте из моего отчета очень много черных точек. А это значит что процент соответствия там 0-25, что крайне удручает. Если говорить про общий процент по миру, то на данный момент только примерно 30 процентов гтфс-поездок (а значит и расписаний) нашли свое соответствие в ОСМ и нашем приложении. С одной стороны это крайне мало, с другой стороны распределение качества соответсвий не равномерное и в некоторых городах осм-сообщество и транспортные компании уже постарались на славу. Ну и мы не сидим на месте.
Со своей стороны буду всячески поддерживать и развивать полезность данного отчета, я верю в него. Также уже есть идеи по автоматическому (частичному) обогащению осм-данных маршрутами из гтфс. Тема с расписанием в приложении довольно новая, появляется только сейчас по мере проработки логики интерфейсов. Расписание можно загрузить как дополнительные данные к карте вместе с другими доп данными: детальными изолиниями, популярными маршрутами. Увидеть его можно если щелкнуть по остановке через которую проходит линия ОТ. Или из просмотра конкретной линии ОТ путем выбора в ней остановки для просмотра. Также хочется отметить что пока расписание будет иметь только информационный характер и не будет участвовать в расчете маршрутов ОТ (всё будет, но чуть позже / я один а вас много). Маршрутизация пока не готова даже банально по той причине что качество покрытия расписанием может желать лучшего, к примеру есть только некоторые автобусы по выбранной остановке. Это может значить что могут быть предложены совсем не оптимальные варианты исходя из наличествующего расписания.
KioskNews shows a cleaned-up reading view extracted from the publisher’s page — the original always lives on their site, not ours.