// Solutions to the Advent Of Code 2024. // Copyright (C) 2025 Stefan Müller // // This program is free software: you can redistribute it and/or modify it under // the terms of the GNU General Public License as published by the Free Software // Foundation, either version 3 of the License, or (at your option) any later // version. // // This program is distributed in the hope that it will be useful, but WITHOUT // ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. // // You should have received a copy of the GNU General Public License along with // this program. If not, see . #include #include #include constexpr int WeightGraph::getInfiniteDistance() { return std::numeric_limits::max(); } int WeightGraph::addVertex(const int weight) { vertexWeights_.push_back(weight); return graph_.addVertex(); } void WeightGraph::addEdge(const int vertex1, const int vertex2, const int weight) { edgeWeights_.push_back(weight); graph_.addEdge(vertex1, vertex2); } int WeightGraph::getVertexWeight(const int vertex) const { return vertexWeights_[vertex]; } int WeightGraph::getEdgeWeight(const int edge) const { return edgeWeights_[edge]; } GraphPathsResult WeightGraph::dijkstra(const int source) const { GraphPathsResult result(graph_.getNVertices(), getInfiniteDistance(), -1); auto compare = [&result](int left, int right) { return result.distances[left] > result.distances[right]; }; std::priority_queue, decltype(compare)> queue{ compare }; result.distances[source] = 0; queue.push(source); while (!queue.empty()) { int v{ queue.top() }; queue.pop(); for (auto neighbor = begin(v); neighbor != end(); ++neighbor) { int newDistance{ result.distances[v] + edgeWeights_[neighbor->edge] }; if (result.distances[neighbor->vertex] > newDistance) { result.distances[neighbor->vertex] = newDistance; result.predecessors[neighbor->vertex] = v; queue.push(neighbor->vertex); } } } return result; } Graph::NeighborIterator WeightGraph::begin(const int vertex) const { return graph_.begin(vertex); } Graph::NeighborIterator WeightGraph::end() const { return graph_.end(); }