D - 混雑する交差点 / Congested Intersection 解説 by admin
Claude 4.6 Opus (Thinking)Overview
This is a problem where, on a graph consisting of intersections and roads, we need to find the shortest time from intersection \(1\) to intersection \(N\), given that passing through congested intersections (those with degree \(K\) or more) incurs an additional cost.
Analysis
Key Observations
Each road takes \(1\) minute to traverse, but when arriving at an intermediate intersection (excluding \(1\) and \(N\)), if that intersection’s degree (number of connected roads) is \(K\) or more, an additional \(1\) minute is required.
In other words, the cost of arriving at intersection \(v\) by traversing edge \((u, v)\) is:
- Base cost: \(1\) (travel time for the road)
- Additional cost: \(+1\) if \(v\) is neither the starting point \(1\) nor the endpoint \(N\), and \(\text{degree}(v) \geq K\)
Since the cost per edge is not uniform (it varies depending on the degree of the destination), this cannot be solved with a simple BFS.
Why Simple BFS Doesn’t Work
BFS can correctly find shortest distances only when all edge costs are equal. In this problem, the cost changes to either \(1\) or \(2\) depending on whether the intersection reached after traversing an edge is congested or not, making the edge weights non-uniform. Therefore, this must be treated as a shortest path problem on a weighted graph.
Algorithm
We solve this using Dijkstra’s algorithm.
Graph Construction: Compute the adjacency list and degree for each intersection.
Edge Cost Definition: When moving from intersection \(u\) to intersection \(v\):
- Cost \(= 1\) (road traversal time)
- If \(v \neq 1\) and \(v \neq N\) and \(\text{degree}(v) \geq K\), then cost \(= 2\) (adding the extra \(1\) minute)
Running Dijkstra’s Algorithm: Starting from intersection \(1\), use a priority queue (min-heap) to find the shortest distances.
Output the Result: Output the shortest distance to intersection \(N\). If it is unreachable, output
-1.
Concrete Example
For example, with \(N=4, M=4, K=3\) and edges \((1,2), (1,3), (2,3), (3,4)\): - Intersection \(3\) has degree \(3\) (\(\geq K\)), so it is a congested intersection - Path \(1 \to 3 \to 4\): cost \(= 1 + (1+1) = 3\) (additional cost at intersection \(3\), since \(3\) is an intermediate intersection) - However, arriving at \(4\) from intersection \(3\) incurs no additional cost since \(4 = N\) - More precisely: \(1 \to 3\) costs \(1\) (intersection \(3\) is intermediate, so \(+1\) for a total of \(2\)), \(3 \to 4\) costs \(1\) (\(N\), so no additional cost). Total: \(3\)
Complexity
- Time complexity: \(O((N + M) \log N)\) (standard complexity of Dijkstra’s algorithm)
- Space complexity: \(O(N + M)\) (adjacency list and distance array for the graph)
Implementation Notes
Do not forget that no additional cost is incurred at the starting point \(1\) and the endpoint \(N\). This corresponds to the problem statement’s condition that “passing is not required at departure and arrival.”
It is efficient to count the degrees while reading the edges.
In Dijkstra’s algorithm, skip entries popped from the queue with a value larger than the already determined distance (
if d > dist[u]: continue) to avoid unnecessary exploration.Since the shortest distance to intersection \(N\) is determined when it is popped from the queue, early termination is possible.
Source Code
import heapq
import sys
input = sys.stdin.readline
def main():
N, M, K = map(int, input().split())
graph = [[] for _ in range(N + 1)]
degree = [0] * (N + 1)
for _ in range(M):
u, v = map(int, input().split())
graph[u].append(v)
graph[v].append(u)
degree[u] += 1
degree[v] += 1
# Dijkstra from node 1 to node N
# Cost of traversing an edge = 1 (travel time)
# Plus, when arriving at a node v (that is not 1 and not N),
# if degree[v] >= K, add 1 extra minute.
INF = float('inf')
dist = [INF] * (N + 1)
dist[1] = 0
pq = [(0, 1)]
while pq:
d, u = heapq.heappop(pq)
if d > dist[u]:
continue
if u == N:
print(d)
return
for v in graph[u]:
# edge cost = 1
# arrival penalty at v: if v != 1 and v != N and degree[v] >= K, add 1
cost = 1
if v != 1 and v != N and degree[v] >= K:
cost += 1
nd = d + cost
if nd < dist[v]:
dist[v] = nd
heapq.heappush(pq, (nd, v))
print(-1 if dist[N] == INF else dist[N])
main()
This editorial was generated by claude4.6opus-thinking.
投稿日時:
最終更新: