BFS - How to Succeed in Algorithms Interview


BFS - How to Succeed in Algorithms Interview

Series: How to Succeed in Algorithms Interview


Applications of BFS

  • Graph, or problems can be converted to graph
  • find shortest path, min value
  • bfs on matrix or indexes on 2 strings

Starting Points

What to add to the queue:

  • edges, boundaries
  • same level elements
  • all nodes

Multiple Starting Points

  • BFS for each point
  • Put all points into queue once
  • BFS

Implementation Detail

  • visited array or set
  • queue stores nodes and their status
  • current state: {current node, visited nodes}
  • bit masks to store visited nodes
  • while (!queue.isEmpty())

Enqueue all Points into Queue first

  • LeetCode 317 - Shortest Distance from All Buildings
    • build a house on an empty land which reaches all buildings in the shortest amount of distance
  • LeetCode 542 - 01 Matrix
    • the initial items in the queue: 0
    • start by adding all the cells with 0s to q.
    • If the new calculated distance for neighbour {i,j} is smaller, we add {i,j} to q and update dist[i][j]
  • [LeetCode 286 - Walls and Gates]
    • Fill each empty room with the distance to its nearest gate
    public void wallsAndGates(int[][] rooms) {
      LinkedList<int[]> list = new LinkedList<int[]>();
      for(int i = 0; i < rooms.length; i++) {
          for(int j = 0; j < rooms[0].length; j++) {
              if(rooms[i][j] == 0)
                  list.add(new int[]{i,j});
          }
      }
      int[][] diff = new int[][]{{-1,0,1,0},{0,1,0,-1}};
      while(!list.isEmpty()) {
          int[] pop = list.remove();
          for(int i = 0; i < diff[0].length; i++) {
              int newR = pop[0] + diff[0][i];
              int newC = pop[1] + diff[1][i];
              if(newR < 0 || newR >= rooms.length || newC < 0 || newC >= rooms[0].length ||
                  rooms[newR][newC] != Integer.MAX_VALUE)
                  continue;
              rooms[newR][newC] = rooms[pop[0]][pop[1]] + 1;
              list.add(new int[]{newR, newC});
          }
      }
    }

Tree - Level Order traverse

public List<List<Integer>> verticalOrder(TreeNode root) {
    if (root == null) return Collections.emptyList();
    Queue<QueueNode> queue = new LinkedList<>();
    Map<Integer, List<Integer>> map = new HashMap<>();
    queue.add(new QueueNode(root, 0));
    int min = 0, max = 0;
    while (!queue.isEmpty()) {
        TreeNode cur = queue.peek().node;
        int depth = queue.poll().depth;
        if (!map.containsKey(depth))
            map.put(depth, new ArrayList<>());
        map.get(depth).add(cur.val);
        min = Math.min(min, depth);
        max = Math.max(max, depth);
        if (cur.left  != null)
            queue.add(new QueueNode(cur.left,  depth - 1));
        if (cur.right != null)
            queue.add(new QueueNode(cur.right, depth + 1));
    }
    List<List<Integer>> ans = new ArrayList<>();
    for (int i = min; i <= max; i ++)
        ans.add(map.get(i));
    return ans;
}

Level Order traverse but without queue

Two(multi) ended bfs

BFS - Unusual

Put same levels into next level queue

Topological sort(BFS)

  • indegree, outdegree,
  • Remove the leaves, update the degrees of inner vertexes

PriorityQueue + BFS

  • Dijkstra single source shortest path
  • time complexity: O(ElogV)

Dijkstra

LeetCode 407 - Trapping Rain Water II
  • from the borders, pick the shortest cell visited and check its neighbors:
  • if the neighbor is shorter, collect the water it can trap and update its height as its height plus the water trapped add all its neighbors to the queue.
LeetCode 364 - Nested List Weight Sum II
LeetCode 743 - Network Delay Time
LeetCode 787 - Cheapest Flights Within K Stops
public int findCheapestPrice(int n, int[][] flights, int src, int dst, int k) {
  Map<Integer, Map<Integer, Integer>> prices = new HashMap<>();
  for (int[] f : flights) {
    if (!prices.containsKey(f[0]))
      prices.put(f[0], new HashMap<>());
    prices.get(f[0]).put(f[1], f[2]);
  }
  Queue<int[]> pq = new PriorityQueue<>((a, b) -> (Integer.compare(a[0], b[0])));
  pq.add(new int[] { 0, src, k + 1 });
  while (!pq.isEmpty()) {
    int[] top = pq.remove();
    int price = top[0];
    int city = top[1];
    int stops = top[2];
    if (city == dst)
      return price;
    if (stops > 0) {
      Map<Integer, Integer> adj = prices.getOrDefault(city, new HashMap<>());
      for (int a : adj.keySet()) {
        pq.add(new int[] { price + adj.get(a), a, stops - 1 });
      }
    }
  }
  return -1;
}

Bellman Ford

int V, E;
Edge edge[];
void BellmanFord(Graph graph,int src)
{
    int V = graph.V, E = graph.E;
    int dist[] = new int[V];
    for (int i=0; i<V; ++i)
        dist[i] = Integer.MAX_VALUE;
    dist[src] = 0;
    for (int i=1; i<V; ++i)
    {
        for (int j=0; j<E; ++j)
        {
            int u = graph.edge[j].src;
            int v = graph.edge[j].dest;
            int weight = graph.edge[j].weight;
            if (dist[u]!=Integer.MAX_VALUE &&
                dist[u]+weight<dist[v])
                dist[v]=dist[u]+weight;
        }
    }
    for (int j=0; j<E; ++j)
    {
        int u = graph.edge[j].src;
        int v = graph.edge[j].dest;
        int weight = graph.edge[j].weight;
        if (dist[u] != Integer.MAX_VALUE &&
            dist[u]+weight < dist[v])
          System.out.println("Graph contains negative weight cycle");
    }
    printArr(dist, V);
}

BFS + Bit mask

BFS + Digit

Jumping Window + Fixed Size

  • LeetCode 683 - K Empty Slots
    public int kEmptySlots(int[] flowers, int k) {
      int[] days = new int[flowers.length];
      for (int i = 0; i < flowers.length; i++) days[flowers[i] - 1] = i + 1;
      int left = 0, right = k + 1, result = Integer.MAX_VALUE;
      for (int i = 0; right < days.length; i++) {
          if (days[i] < days[left] || days[i] <= days[right]) {
              if (i == right)
                  result = Math.min(result, Math.max(days[left], days[right]));
              left = i;
              right = k + 1 + i;
          }
      }
      return (result == Integer.MAX_VALUE) ? -1 : result;
    }

Classic BFS Questions

Labels

adsense (5) Algorithm (69) Algorithm Series (35) Android (7) ANT (6) bat (8) Big Data (7) Blogger (14) Bugs (6) Cache (5) Chrome (19) Code Example (29) Code Quality (7) Coding Skills (5) Database (7) Debug (16) Design (5) Dev Tips (63) Eclipse (32) Git (5) Google (33) Guava (7) How to (9) Http Client (8) IDE (7) Interview (88) J2EE (13) J2SE (49) Java (186) JavaScript (27) JSON (7) Learning code (9) Lesson Learned (6) Linux (26) Lucene-Solr (112) Mac (10) Maven (8) Network (9) Nutch2 (18) Performance (9) PowerShell (11) Problem Solving (11) Programmer Skills (6) regex (5) Scala (6) Security (9) Soft Skills (38) Spring (22) System Design (11) Testing (7) Text Mining (14) Tips (17) Tools (24) Troubleshooting (29) UIMA (9) Web Development (19) Windows (21) xml (5)