черновик · текст собрал Claude по репозиториям и заметкам, перепишу сам
Финальный проект курса C++, сентябрь–октябрь 2024 года.
Программа хранит остановки с координатами и автобусные маршруты и отвечает на запросы: сколько остановок на маршруте, какая у него длина, какие автобусы проходят через остановку. Длина считается по реальным дорожным расстояниям, и программа сравнивает её с расстоянием по прямой — получается «извилистость» маршрута.
Этапы
Сначала был текстовый ввод (он остался в репозитории cpp-bus-directory). Потом — дорожные расстояния. На последнем этапе ввод и вывод перешли на JSON, а по запросу Map программа рисует карту маршрутов в SVG: линии автобусов разными цветами, подписи маршрутов и остановок.
Внутри несколько модулей: каталог, JSON-библиотека, SVG-библиотека, рендерер карты и обработчик запросов. Остановки хранятся в std::deque, чтобы указатели на них не ломались при добавлении новых, а для расстояний между парами остановок есть свой хешер.
Код писал руками, и времени на рефакторинг не хватило — это видно. Оставляю проект как есть.
Фрагмент
Добавление маршрута: дорожная длина, длина по прямой и их отношение.
void TransportCatalogue::AddBus(std::string_view name, std::vector<std::string_view> route, bool is_roundtrip) {
double fact_route_length = 0.0;
double geo_route_length = 0.0;
for (auto it = route.begin() + 1; it != route.end(); ++it) {
auto prev_stop = stopname_to_stop_.find(*(it - 1));
auto stop = stopname_to_stop_.find(*it);
fact_route_length +=
distance_between_stops_.count(std::make_pair(prev_stop->second, stop->second))
? distance_between_stops_.at(std::make_pair(prev_stop->second, stop->second))
: distance_between_stops_.at(std::make_pair(stop->second, prev_stop->second));
geo_route_length += ComputeDistance(prev_stop->second->coordinates, stop->second->coordinates);
}
double route_curvature = fact_route_length / geo_route_length;
buses_.emplace_back(Bus{std::string(name), {}, fact_route_length, route_curvature, is_roundtrip});
for (const auto& stop_name : route) {
buses_.back().route.push_back(stopname_to_stop_.at(std::string(stop_name)));
}
busname_to_bus_[buses_.back().name] = &buses_.back();
}