昨晚考研的朋友发来这道题,平日很少接触图的算法,只会深度优先遍历和层次优先遍历,正好可以巩固一下。自己简单测了几组数据,都没问题。不知道有没有存在隐藏的bug,如果有人可以帮我指出感激不尽。
关于图结点的类
class Node {
public int val;
public List<Node> children;
public Node() {
}
public Node(int _val) {
val = _val;
}
public Node(int _val, List<Node> _children) {
val = _val;
children = _children;
}
@Override
public String toString() {
return "Node{" +
"val=" + val +
'}';
}
}
构造测试
Node n1 = new Node(1);
Node n2 = new Node(2);
Node n3 = new Node(3);
Node n4 = new Node(4);
Node n5 = new Node(5);
Node n6 = new Node(6);
List<Node> list1 = new ArrayList<>();
list1.add(n2);
list1.add(n6);
n1.children = list1;
List<Node> list2 = new ArrayList<>();
list2.add(n1);
n2.children = list2;
List<Node> list3 = new ArrayList<>();
list3.add(n4);
n3.children = list3;
List<Node> list4 = new ArrayList<>();
list4.add(n5);
list4.add(n6);
n4.children = list4;
List<Node> list5 = new ArrayList<>();
list5.add(n4);
n5.children = list5;
List<Node> list6 = new ArrayList<>();
list6.add(n4);
list6.add(n1);
n6.children = list6;
System.out.println(longestNode(n1));
大概长这个样子 勿吐槽
算法实现
思路:使用队列来广度优先遍历,另外用哈希表存放已经访问过的结点
public Node longestNode(Node node){
if (node==null)
return null;
HashSet<Node> set = new HashSet<>(); //存放已经经过
set.add(node);
LinkedList<Node> queue = new LinkedList<>(); //使用队列来广度优先遍历
queue.add(node);
while (true){
int size = queue.size();
while (size>0){
Node last = queue.pollLast();
List<Node> list = last.children;
boolean flag = false; //记录是否有新的结点
for (Node n:list
) {
if (!set.contains(n)){
set.add(n);
queue.addLast(n);
flag = true;
}
}
if (!flag){ //如果没有新的未遍历结点 说明最后这个结点是最远的
return last;
}
size --;
}
}
}