[LeetCode] 261. Graph Valid Tree _ Medium tag: BFS
2018-07-06 04:30 Johnson_强生仔仔 阅读(315) 评论(0) 编辑 收藏 举报Given n
nodes labeled from 0
to n-1
and a list of undirected edges (each edge is a pair of nodes), write a function to check whether these edges make up a valid tree.
Example 1:
Input:n = 5
, andedges = [[0,1], [0,2], [0,3], [1,4]]
Output: true
Example 2:
Input:n = 5,
andedges = [[0,1], [1,2], [2,3], [1,3], [1,4]]
Output: false
Note: you can assume that no duplicate edges will appear in edges
. Since all edges are undirected, [0,1]
is the same as [1,0]
and thus will not appear together in edges
.
这个题的思路就是BFS, 另外注意有效的tree的条件是nodes number == number of edges + 1 and connects all nodes, 所以首先用这个条件去掉所有点连通并且有loop的情况, 所以还有两种情况, 一种是valid tree, 另一种是有重复的loop, 但是不连通, 所以我们用BFS选择任一点开始, 我们选择0, 因为所有情况都包括0这个node, 然后BFS, 最后把visited set的size跟input n比较是否相等, 如果相等, valid, 否则不valid.
1. Constraints
1) n <=0 时, False
2) n =1是, edge = [] => True
3) no duplicates and (1,0) and (0,1) will not exist at same time, 这个条件保证了nodes number == number of edges + 1 的判断依据
2. Ideas
BFS T: O(n) S: O(n)
1) edge case, n <=0 时, False
2) transform input into a dictionary
3) start from 0 , BFS, save all visited nodes into a visited set
4) return len(visited) == n
3. Code
1 class Solution: 2 def validTree(self, n, edges): 3 if n <= 0: return False 4 d, queue, visited = collections.defaultdict(set), collections.deque([0]), set([0]) 5 for n1, n2 in edges: 6 d[n1].add(n2) 7 d[n2].add(n1) 8 while queue: 9 node = queue.popleft() 10 for each in d[node]: 11 if each not in visited: 12 queue.append(node) 13 visited.add(node) 14 return len(visited) == n
2. Use Union find, 思路参考这里,如果最后只剩一个集合,那表明是valid tree,要达到最后只剩一个集合,那么每次的edge都必须有两个set的合并,如果没有,那么返回False
Code : T: O(n * α(n)), α is the Inverse Ackermann Function
class UnionFind: def __init__(self, n): self.parent = [node for node in range(n)] def find(self, A): while A != self.parent[A]: A = self.parent[A] return A def union(self, A, B): rootA= self.find(A) rootB = self.find(B) if rootA == rootB: return False self.parent[rootA] = rootB return True class Solution: def validTree(self, n: int, edges: List[List[int]]) -> bool: if len(edges) != n - 1: return False unionFind = UnionFind(n) for e1, e2 in edges: if not unionFind.union(e1, e2): return False return True
4. Test cases
1) 1, [] => True
2) 3, [[0,1], [0,2]] => True
3) 5, [[0,1], [3, 4], [3,5], [4,5]] => False