310. 最小高度树 --bfs(重点掌握)

对于一个具有树特征的无向图,我们可选择任何一个节点作为根。图因此可以成为树,在所有可能的树中,具有最小高度的树被称为最小高度树。给出这样的一个图,写出一个函数找到所有的最小高度树并返回他们的根节点。

格式

该图包含 n 个节点,标记为 0 到 n - 1。给定数字 n 和一个无向边 edges 列表(每一个边都是一对标签)。

你可以假设没有重复的边会出现在 edges 中。由于所有的边都是无向边, [0, 1]和 [1, 0] 是相同的,因此不会同时出现在 edges 里。

示例 1:

输入: n = 4, edges = [[1, 0], [1, 2], [1, 3]]

    0
    |
    1
   / \
  2   3 

输出: [1]
示例 2:

输入: n = 6, edges = [[0, 3], [1, 3], [2, 3], [4, 3], [5, 4]]

 0  1  2
  \ | /
    3
    |
    4
    |
    5 

输出: [3, 4]
说明:

根据树的定义,树是一个无向图,其中任何两个顶点只通过一条路径连接。 换句话说,一个任何没有简单环路的连通图都是一棵树。

树的高度是指根节点和叶子节点之间最长向下路径上边的数量。

思路 拓扑序列 每次除去度为1 的节点 最后剩下的节点就是生成树的根节点

class Solution {
    public List<Integer> findMinHeightTrees(int n, int[][] edges) {
      List<Integer> ans = new ArrayList<Integer>();
      //建立一个 存放点信息的 list
      List<List<Integer>> map = new ArrayList<>();
         if (n == 1){
            ans.add(0);
            return ans;
        }
      // 有n个节点 所以进行初始化
      for (int i=0;i<n;i++) {
            map.add(new ArrayList<>());
        }
        // 每个节点都有一个度 
        int [] degree = new int [n];
      // edgs[0] 代表第一组 边 edgs[0][0] :第一组边的第一个节点 edgs[0][1] :第一组边中的第二个节点 
      for(int i=0;i<edges.length;i++){
          //每次通过 edges[i] 拿到的是一组边

          // 找到对应的点 度数++
          degree[edges[i][0]]++;
          degree[edges[i][1]]++;

         //将每个点 放入map中 加入其相邻点队  ?? 这一步意义何为
         map.get(edges[i][0]).add(edges[i][1]);
         map.get(edges[i][1]).add(edges[i][0]);
      }
      // bfs 必备队列
       Queue<Integer> queue = new LinkedList<>();

//      3.在队列中加入第一个满足条件的元素
        for (int i = 0;i < n;i++){
            if (degree[i] == 1){//度数为1,说明是叶子结点,入队列
                queue.offer(i);
            }
        }

 //进入while循环 剪枝更新 
    while(!queue.isEmpty()){
        //初始化 ans
       ans=new ArrayList<>();
       //对现在所有队列中元素进行出队列 删除的操作 同时更新 其相邻的节点的度
       int size = queue.size();
       //此处不能使用 i
       for(int i=0 ; i<size; i++){
           
           int temp = queue.poll();
           ans.add(temp);
           // 获得当前节点的相邻节点 
           List<Integer> nexts = map.get(temp);
           for(Integer next : nexts){
                    degree[next]--;
                    if(degree[next]==1){
                        //加入进队列
                        queue.offer(next);
                    }
           }
           

       }
    }


System.out.println("ans is "+ ans);
return ans;

    }
}

你可能感兴趣的:(复试学习)