最小高度树
该图包含 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]
思路+代码+注释:
class Graph{
private LinkedList<Integer>[] lists;
public Graph(int n) {
this.lists = new LinkedList[n];
for (int i = 0; i < n; i++) {
lists[i]=new LinkedList<>();
}
}
private void add(int s,int e)
{
lists[s].add(e);
lists[e].add(s);
}
}
public List<Integer> findMinHeightTrees(int n, int[][] edges) {
/*
思路:总体思路是从叶子节点开始一层一层往上剥,找到根节点
构建图,找可到节点数为1的节点(叶子节点),将所有叶子节点添加到集合中,遍历所有叶子节点将该叶子节点从其他节点可到集合中删除,如果其他节点删除
后可到集合为1那么将这些新叶子节点添加到新集合中,进行下一轮遍历,每次遍历一轮叶子节点,节点数n减去删除的叶子节点数,当n小于等于2时结束,最终的结果就是
最终list中的节点
*/
if (n==1)
{
List<Integer> res=new ArrayList<>();
res.add(0);
return res;
}
Graph graph=new Graph(n);
List<Integer> res=new ArrayList<>();
for (int i = 0; i < edges.length; i++) {
int[] edge=edges[i];
graph.add(edge[0],edge[1]);
}
LinkedList<Integer>[] list=graph.lists;
for (int i = 0; i < list.length; i++) {
if (list[i].size()==1)
{
res.add(i);
}
}
while (n>2)
{
n-=res.size();
List<Integer> newRes=new ArrayList<>();
for (Integer i:res
) {
Integer target=list[i].get(0);
list[target].remove(i);
if (list[target].size()==1)
{
newRes.add(target);
}
}
res=newRes;
}
return res;
}