宽度优先搜索

Java

Queue queue = new LinkedList<>();
String[] vals = String.split(" ");
int result = Integer.parseInt(String);
Collections.reverse(List);
new int[]{1,0};
  1. BFS应用场景
    图的遍历 Traversal in Graph
  • 层级遍历 Level Order Traversal
  • 由点及面 Connected Component
  • 拓扑排序 Topological Sorting

最短路径 Shortest Path in Simple Graph

  • 仅限简单图求最短路径
  • 即,图中每条边长度都是1,或者边长都相等

非递归的方式找所有方案 Iteration solution for all possible results
• 这一点我们将在后面 DFS 的课上提到

  1. 复杂度
    二叉树 时间O(V) 空间:同层节点个数最大值
    图 时间O(V+E) 空间:最大深度
    优化方案 双向BFS Bidirectional BFS
  • 假设单向BFS需要搜索 N 层才能到达终点,每层的判断量为 X,那么总的运算量为 X ^ N 如果换成是双向BFS,前后各自需要搜索 N / 2 层,总运算量为 2 * X ^ (N / 2)
  • 无向图; 所有边的长度都为 1 或者长度都一样; 同时给出了起点和终点
  1. 二叉树上的BFS
    102 Binary Tree Level Order Traversal
    297 Serialize and Deserialize Binary Tree
  • 访问到节点的时候 在结果字符串上添加当前节点信息
  • serialize时候空节点也入队 否则无法表示空节点
  1. 图上的BFS
    注意节点不要重复入队就好
    133 Clone Graph
    *127 Word Ladder
    *261 Graph Valid Tree
    lt431 Connected Component in Undirected Graph
  1. 矩阵上的BFS
    200 Number of Islands 四个
    lt611 Knight Shortest Path 八个
    *lt598 Zombie in Matrix
    lt573 Build Post Office II

  2. 拓扑排序
    算法描述:
    统计每个点的入度
    将每个入度为 0 的点放入队列(Queue)中作为起始节点
    不断从队列中拿出一个点,去掉这个点的所有连边(指向其他点的边),其他点的相应的入度 - 1
    一旦发现新的入度为 0 的点,丢回队列中

求任意一个拓扑排序
lt127 Topological Sorting
210 Course Schedule II
*269 Alien Dictionary 注意可能会有重复的字符对 这种情况下入度不更新
求是否存在拓扑排序
207 Course Schedule
求是否存在且仅存在一个拓扑序 Queue中最多同时只有1个节点
*444 Sequence Reconstruction
注意 重复对不能重复统计入度
求所有的拓扑序 DFS

102 Binary Tree Level Order Traversal

/**
 * Definition of TreeNode:
 * public class TreeNode {
 *     public int val;
 *     public TreeNode left, right;
 *     public TreeNode(int val) {
 *         this.val = val;
 *         this.left = this.right = null;
 *     }
 * }
 */

public class Solution {
    /**
     * @param root: A Tree
     * @return: Level order a list of lists of integer
     */
    public List> levelOrder(TreeNode root) {
        // write your code here
        List> results = new ArrayList<>();
        if(root==null)
            return results;
        Queue queue = new LinkedList<>();
        queue.offer(root);
        while(!queue.isEmpty()){
            int size = queue.size();
            List list = new ArrayList<>();
            for(int i=0; i

297 Serialize and Deserialize Binary Tree

/**
 * Definition of TreeNode:
 * public class TreeNode {
 *     public int val;
 *     public TreeNode left, right;
 *     public TreeNode(int val) {
 *         this.val = val;
 *         this.left = this.right = null;
 *     }
 * }
 */


public class Solution {
    /**
     * This method will be invoked first, you should design your own algorithm 
     * to serialize a binary tree which denote by a root node to a string which
     * can be easily deserialized by your own "deserialize" method later.
     */
    public String serialize(TreeNode root) {
        // write your code here
        StringBuilder sb = new StringBuilder();
        if(root==null){
            return sb.toString();
        }
        Queue queue = new LinkedList<>();
        queue.offer(root);
        while(!queue.isEmpty()){
            TreeNode node = queue.poll();
            if(node==null){
                sb.append("# ");
                continue;
            }
            sb.append(node.val);
            sb.append(" ");
            queue.offer(node.left);
            queue.offer(node.right);
        }
        return sb.toString();
    }

    /**
     * This method will be invoked second, the argument data is what exactly
     * you serialized at method "serialize", that means the data is not given by
     * system, it's given by your own serialize method. So the format of data is
     * designed by yourself, and deserialize it here as you serialize it in 
     * "serialize" method.
     */
    public TreeNode deserialize(String data) {
        // write your code here
        if(data==null || data.length()==0)
            return null;
        String[] vals = data.split(" ");
        TreeNode root = new TreeNode(Integer.parseInt(vals[0]));
        Queue queue = new LinkedList<>();
        queue.offer(root);
        int index = 1;
        while(!queue.isEmpty()){
            TreeNode node = queue.poll();
            if(vals[index].equals("#")){
                node.left = null;
            }else{
                node.left = new TreeNode(Integer.parseInt(vals[index]));
                queue.offer(node.left);
            }
            index++;
            if(vals[index].equals("#")){
                node.right = null;
            }else{
                node.right = new TreeNode(Integer.parseInt(vals[index]));
                queue.offer(node.right);
            }
            index++;
        }
        return root;
    }
}

133 Clone Graph

/**
 * Definition for undirected graph.
 * class UndirectedGraphNode {
 *     int label;
 *     ArrayList neighbors;
 *     UndirectedGraphNode(int x) { label = x; neighbors = new ArrayList(); }
 * };
 */


public class Solution {
    /*
     * @param node: A undirected graph node
     * @return: A undirected graph node
     */
    public UndirectedGraphNode cloneGraph(UndirectedGraphNode node) {
        // write your code here
        if(node==null)
            return null;
        UndirectedGraphNode newroot = new UndirectedGraphNode(node.label);
        Map map = new HashMap<>();
        map.put(node, newroot);
        Queue queue = new LinkedList<>();
        queue.offer(node);
        while(!queue.isEmpty()){
            UndirectedGraphNode current = queue.poll();
            for(UndirectedGraphNode neighbor: current.neighbors){
                UndirectedGraphNode newNeighbor;
                if(!map.containsKey(neighbor)){
                    newNeighbor = new UndirectedGraphNode(neighbor.label);
                    map.put(neighbor, newNeighbor);
                    queue.offer(neighbor);
                }
                newNeighbor = map.get(neighbor);
                UndirectedGraphNode newCurrent = map.get(current);
                newCurrent.neighbors.add(newNeighbor);
            }
        }
        return newroot;
    }
}

127 Word Ladder

class Solution {
    public int ladderLength(String beginWord, String endWord, List wordList) {
        Set set = new HashSet<>();
        for(String str : wordList){
            set.add(str);
        }
        int result = 2;
        if(!set.contains(endWord))
            return 0;
        if(beginWord.equals(endWord))
            return 1;
        Queue queue = new LinkedList<>();
        Set visited = new HashSet<>();
        visited.add(beginWord);
        queue.offer(beginWord);
        while(!queue.isEmpty()){
            
            int size = queue.size();
            for(int i=0; i getNextWords(Set set, String str, Set visited){
        List result = new ArrayList<>();
        char[] chars = str.toCharArray();
        for(int i=0; i

261 Graph Valid Tree

class Solution {
    public boolean validTree(int n, int[][] edges) {
        return bfs(n, edges);
    }
    private boolean bfs(int n, int[][] edges){
        if(edges.length!=n-1)
            return false;
        Map> graph = new HashMap<>();
        for(int[] edge : edges){
            int n0 = edge[0];
            int n1 = edge[1];
            Set set0 = graph.getOrDefault(n0, new HashSet<>());
            Set set1 = graph.getOrDefault(n1, new HashSet<>());
            set0.add(n1);
            set1.add(n0);
            graph.put(n0, set0);
            graph.put(n1, set1);
        }
        Queue queue = new LinkedList<>();
        Set visited = new HashSet<>();
        queue.offer(0);
        visited.add(0);
        int count = 0;
        while(!queue.isEmpty()){
            int current = queue.poll();
            count++;
            for(Integer next : graph.getOrDefault(current, new HashSet<>())){
                if(visited.contains(next))
                    return false;
                visited.add(next);
                Set set = graph.get(next);
                set.remove(current);
                graph.put(next, set);
                queue.offer(next);
            }
        }
        System.out.println(count);
        return count == n;
    }
}

lt431 Connected Component in Undirected Graph

/**
 * Definition for Undirected graph.
 * class UndirectedGraphNode {
 *     int label;
 *     ArrayList neighbors;
 *     UndirectedGraphNode(int x) { label = x; neighbors = new ArrayList(); }
 * };
 */


public class Solution {
    /*
     * @param nodes: a array of Undirected graph node
     * @return: a connected set of a Undirected graph
     */
    public List> connectedSet(List nodes) {
        // write your code here
        if(nodes==null)
            return null;
        Set set = new HashSet<>();
        List> result = new ArrayList<>();
        for(UndirectedGraphNode node: nodes){
            if(!set.contains(node)){
                set.add(node);
                List temp = getBFS(nodes, node, set);
                result.add(temp);
            }
        }
        return result;
    }
    private List getBFS(List nodes, UndirectedGraphNode node, Set set){
        List result = new ArrayList<>();
        Queue queue = new LinkedList<>();
        queue.offer(node);
        while(!queue.isEmpty()){
            UndirectedGraphNode temp = queue.poll();
            result.add(temp.label);
            for(UndirectedGraphNode neighbor: temp.neighbors){
                if(!set.contains(neighbor)){
                    queue.offer(neighbor);
                    set.add(neighbor);
                }
            }
        }
        Collections.sort(result);
        return result;
    }
}

200 Number of Islands

class Solution {
    public int numIslands(char[][] grid) {
        if(grid==null || grid.length==0 || grid[0]==null || grid[0].length==0)
            return 0;
        int result = 0;
        boolean[][] visited = new boolean[grid.length][grid[0].length];
        for(int i=0; i queue = new LinkedList<>();
        queue.offer(new int[]{i, j});
        while(!queue.isEmpty()){
            int[] current = queue.poll();
            for(int k=0; k<4; k++){
                int x = current[0]+dirx[k];
                int y = current[1]+diry[k];
                if(isValid(visited, x, y, grid)){
                    queue.offer(new int[]{x, y});
                    grid[x][y] = '0';
                    visited[x][y] = true;
                }
            }
        }
    }
    private boolean isValid(boolean[][] visited, int x, int y, char[][] grid){
        return x>=0 && x=0 && y

lt611 Knight Shortest Path

/**
 * Definition for a point.
 * class Point {
 *     int x;
 *     int y;
 *     Point() { x = 0; y = 0; }
 *     Point(int a, int b) { x = a; y = b; }
 * }
 */

public class Solution {
    /**
     * @param grid: a chessboard included 0 (false) and 1 (true)
     * @param source: a point
     * @param destination: a point
     * @return: the shortest path 
     */
    public int shortestPath(boolean[][] grid, Point source, Point destination) {
        // write your code here
        if(grid==null || grid.length==0 || grid[0]==null || grid[0].length==0)
            return 0;
        if(source.x==destination.x && source.y==destination.y)
            return 0;
        Queue queue = new LinkedList<>();
        queue.offer(new int[]{source.x, source.y});
        int[] dirx = {1, -1, 2, 2, 1, -1, -2, -2};
        int[] diry = {2, 2, 1, -1, -2, -2, 1, -1};
        boolean[][] visited = new boolean[grid.length][grid[0].length];
        visited[source.x][source.y] = true;
        int result = 0;
        while(!queue.isEmpty()){
            result++;
            int size = queue.size();
            System.out.println(size);
            for(int i=0; i=0 && x=0 && y

598 Zombie in Matrix

public class Solution {
   /**
    * @param grid: a 2D integer grid
    * @return: an integer
    */
   public int zombie(int[][] grid) {
       // write your code here
       Queue queue = new LinkedList<>();
       for(int i=0; i=0 && x=0 && y

127 Topological Sorting

/**
 * Definition for Directed graph.
 * class DirectedGraphNode {
 *     int label;
 *     ArrayList neighbors;
 *     DirectedGraphNode(int x) { label = x; neighbors = new ArrayList(); }
 * };
 */

public class Solution {
    /*
     * @param graph: A list of Directed graph node
     * @return: Any topological order for the given graph.
     */
    public ArrayList topSort(ArrayList graph) {
        // write your code here
        Map map = new HashMap<>();
        for(DirectedGraphNode node : graph){
            for(DirectedGraphNode neighbor : node.neighbors){
                map.put(neighbor, map.getOrDefault(neighbor, 0)+1);
            }
        }
        Queue queue = new LinkedList<>();
        for(DirectedGraphNode node : graph){
            if(!map.containsKey(node)){
                queue.offer(node);
            }
        }
        ArrayList result = new ArrayList<>();
        while(!queue.isEmpty()){
            DirectedGraphNode node = queue.poll();
            result.add(node);
            for(DirectedGraphNode neighbor : node.neighbors){
                map.put(neighbor, map.get(neighbor)-1);
                if(map.get(neighbor)==0)
                    queue.offer(neighbor);
            }
        }
        return result;
    }
}

210 Course Schedule II

class Solution {
    public int[] findOrder(int numCourses, int[][] prerequisites) {
        Map map = new HashMap<>();
        Map> graph = new HashMap<>();
        for(int[] prerequest : prerequisites){
            int in = prerequest[0];
            int out = prerequest[1];
            map.put(in, map.getOrDefault(in,0)+1);
            List neighbors = graph.getOrDefault(out, new ArrayList<>());
            neighbors.add(in);
            graph.put(out, neighbors);
        }
        Queue queue = new LinkedList<>();
        for(int i=0; i())){
                map.put(in, map.get(in)-1);
                if(map.get(in)==0)
                    queue.offer(in);
            }
        }
        if(count==numCourses)
            return result;
        return new int[0];
    }
}

269 Alien Dictionary

class Solution {
    public String alienOrder(String[] words) {
        Map> graph = new HashMap<>();
        Map indegree = new HashMap<>();
        Set alphabet = new HashSet<>();
        for(String word : words){
            for(int i=0; i set = graph.getOrDefault(pre.charAt(j), new HashSet<>());
                    if(set.add(next.charAt(j))){
                        graph.put(pre.charAt(j), set);
                        indegree.put(next.charAt(j), indegree.getOrDefault(next.charAt(j), 0)+1);
                    }
                    break;
                }
            }
        }
        StringBuilder sb = new StringBuilder();
        Queue queue = new LinkedList<>();
        for(Character c : alphabet){
            if(!indegree.containsKey(c)){
                queue.offer(c);
            }
        }
        while(!queue.isEmpty()){
            Character c = queue.poll();
            sb.append(c);
            for(Character next : graph.getOrDefault(c, new HashSet<>())){
                indegree.put(next, indegree.get(next)-1);
                if(indegree.get(next)==0)
                    queue.offer(next);
            }
        }
        if(sb.length()==alphabet.size()){
            return sb.toString();
        }
        return "";
    }
}

207 Course Schedule

class Solution {
    public boolean canFinish(int numCourses, int[][] prerequisites) {
        Map map = new HashMap<>();
        Map> graph = new HashMap<>();
        for(int[] prerequest : prerequisites){
            int in = prerequest[0];
            int out = prerequest[1];
            map.put(in, map.getOrDefault(in,0)+1);
            List neighbors = graph.getOrDefault(out, new ArrayList<>());
            neighbors.add(in);
            graph.put(out, neighbors);
        }
        Queue queue = new LinkedList<>();
        for(int i=0; i())){
                map.put(in, map.get(in)-1);
                if(map.get(in)==0)
                    queue.offer(in);
            }
        }
        return count==numCourses;
    }
}

444 Sequence Reconstruction

class Solution {
    public boolean sequenceReconstruction(int[] org, List> seqs) {
        // write your code here
        Map indegree = new HashMap<>();
        Map> graph = new HashMap<>();
        
        int index = 0;
        for(List seq : seqs){
            for(int i=1; iorg.length || out>org.length)
                    return false;
                if(!graph.containsKey(in)){
                    graph.put(in, new HashSet<>());
                }
                Set set = graph.getOrDefault(out, new HashSet<>());
                if(set.add(in)){
                    graph.put(out, set);
                    indegree.put(in, indegree.getOrDefault(in, 0)+1);
                }
                
            }
        }
        System.out.println(indegree.size());
        System.out.println(graph.size());
        Queue queue = new LinkedList<>();
        if(indegree.containsKey(org[0]))
            return false;
        queue.offer(org[0]);
        while(!queue.isEmpty()){
            Integer current = queue.poll();
            if(org[index]!=current)
                return false;
            index++;
            for(Integer next : graph.getOrDefault(current, new HashSet<>())){
                indegree.put(next, indegree.get(next)-1);
                if(indegree.get(next)==0)
                    queue.offer(next);
            }
            if(queue.size()>1)
                return false;
        }
        return index==org.length;
    }
}

你可能感兴趣的:(宽度优先搜索)