Shortest Distance After Road Addition Queries I

medium graph bfs shortest path

Problem

There are n cities numbered 0 to n-1. Initially there is a one-way road from every city i to city i+1, so the only way to travel is forward step by step. Each query [u, v] adds a new one-way road from u to v (with u < v). After processing each query, return the length of the shortest path from city 0 to city n-1 measured in number of roads. The answer to each query is independent of later queries but the roads accumulate.

Inputn = 5, queries = [[2,4],[0,2],[0,4]]
Output[3, 2, 1]
After [2,4]: 0→1→2→4 = 3. After [0,2]: 0→2→4 = 2. After [0,4]: 0→4 = 1.

from collections import deque

def shortest_distance(n, queries):
    adj = [[i + 1] for i in range(n - 1)]
    adj.append([])
    ans = []
    for u, v in queries:
        adj[u].append(v)
        dist = [-1] * n
        dist[0] = 0
        q = deque([0])
        while q:
            x = q.popleft()
            for y in adj[x]:
                if dist[y] == -1:
                    dist[y] = dist[x] + 1
                    q.append(y)
        ans.append(dist[n - 1])
    return ans
function shortestDistance(n, queries) {
  const adj = Array.from({ length: n }, (_, i) => i < n - 1 ? [i + 1] : []);
  const ans = [];
  for (const [u, v] of queries) {
    adj[u].push(v);
    const dist = new Array(n).fill(-1);
    dist[0] = 0;
    const q = [0];
    let head = 0;
    while (head < q.length) {
      const x = q[head++];
      for (const y of adj[x]) {
        if (dist[y] === -1) {
          dist[y] = dist[x] + 1;
          q.push(y);
        }
      }
    }
    ans.push(dist[n - 1]);
  }
  return ans;
}
class Solution {
    public int[] shortestDistanceAfterQueries(int n, int[][] queries) {
        List<List<Integer>> adj = new ArrayList<>();
        for (int i = 0; i < n; i++) {
            adj.add(new ArrayList<>());
            if (i < n - 1) adj.get(i).add(i + 1);
        }
        int[] ans = new int[queries.length];
        for (int qi = 0; qi < queries.length; qi++) {
            adj.get(queries[qi][0]).add(queries[qi][1]);
            int[] dist = new int[n];
            Arrays.fill(dist, -1);
            dist[0] = 0;
            Deque<Integer> q = new ArrayDeque<>();
            q.add(0);
            while (!q.isEmpty()) {
                int x = q.poll();
                for (int y : adj.get(x)) {
                    if (dist[y] == -1) {
                        dist[y] = dist[x] + 1;
                        q.add(y);
                    }
                }
            }
            ans[qi] = dist[n - 1];
        }
        return ans;
    }
}
class Solution {
public:
    vector<int> shortestDistanceAfterQueries(int n, vector<vector<int>>& queries) {
        vector<vector<int>> adj(n);
        for (int i = 0; i < n - 1; i++) adj[i].push_back(i + 1);
        vector<int> ans;
        for (auto& qr : queries) {
            adj[qr[0]].push_back(qr[1]);
            vector<int> dist(n, -1);
            dist[0] = 0;
            queue<int> q;
            q.push(0);
            while (!q.empty()) {
                int x = q.front(); q.pop();
                for (int y : adj[x]) {
                    if (dist[y] == -1) {
                        dist[y] = dist[x] + 1;
                        q.push(y);
                    }
                }
            }
            ans.push_back(dist[n - 1]);
        }
        return ans;
    }
};
Time: O(q · (n + q)) Space: O(n + q)