题目:
给你无向 连通 图中一个节点的引用,请你返回该图的 深拷贝(克隆)。
图中的每个节点都包含它的值 val(int) 和其邻居的列表(list[Node])。
算法:
方法一:DFS
联通图的遍历,为了避免死循环,通过hash数组标记是否访问过
func cloneGraph(node *Node) *Node {
if node == nil {
return nil
}
copyed := make(map[*Node]*Node)
var dfs func(graphNode *Node) *Node
dfs = func(graphNode *Node) *Node {
if graphNode == nil {
return nil
}
if cp, ok := copyed[graphNode]; ok {
return cp
}
copyNode := &Node{Val:graphNode.Val}
copyed[graphNode] = copyNode
for i := range graphNode.Neighbors {
copyNode.Neighbors = append(copyNode.Neighbors, dfs(graphNode.Neighbors[i]))
}
return copyNode
}
return dfs(node)
}
方法二:BFS
hash保存原始节点和copy节点的映射关系,先将node节点copy,
queue保存Neighbors没有copy的节点,遍历queue.Neighbors,如果Neighbor没有copy,则new一个对象,放到hash中,有copy则直接将copy复制到当前节点的Neighbors中。
func cloneGraph(node *Node) *Node {
if node == nil {
return nil
}
queue := []*Node{node}
// hash保存原始节点val和copy节点的映射关系
hash := make([]*Node, 101)
hash[node.Val] = &Node{Val:node.Val}
for len(queue) != 0 {
popedNode := queue[0]
queue = queue[1:]
for i := range popedNode.Neighbors {
if hash[popedNode.Neighbors[i].Val] == nil {
hash[popedNode.Neighbors[i].Val] = &Node{Val:popedNode.Neighbors[i].Val}
queue = append(queue, popedNode.Neighbors[i])
}
hash[popedNode.Val].Neighbors = append(hash[popedNode.Val].Neighbors, hash[popedNode.Neighbors[i].Val])
}
}
return hash[node.Val]
}