力扣第133题-克隆图

161 阅读2分钟

Offer 驾到,掘友接招!我正在参与2022春招打卡活动,点击查看活动详情

前言

力扣第133题 克隆图 如下所示:

给你无向 连通 图中一个节点的引用,请你返回该图的 深拷贝(克隆)。

图中的每个节点都包含它的值 valint) 和其邻居的列表(list[Node])。

class Node {
    public int val;
    public List<Node> neighbors;
}

示例 1:

image.png

image.png

一、思路

我们首先要了解一下什么是 深拷贝?深拷贝是指:根据原对象复制一个内容相同的目标对象,原对象和目标对象间相互独立,无任何关联关系。

除此之外,还需要了解一下 无向连通图这是指:任何两个节点间都是连同的图。如下所示:

image.png

因为图为 无向连通图,我们就可以根据任何一个节点遍历到图中所有的节点,就可以很轻松的还原整个图了。大致的步骤如下所示:

  1. 克隆当前节点,新节点为 targetNode
  2. 克隆当前节点的邻居节点 newNeighbors,并将新的邻居节点 newNeighbors 作为 targetNode 的邻居节点。
  3. 重复步骤 1 和 2

在克隆图的过程中,我们为了防止重复访问节点。我们需要构建一个一原节点 Node 作为 key 的哈希表,当当前节点 Node 在哈希表中存在时,则表示已访问过了,则无需访问了。

综上所述,我们可以使用 递归 来实现这一想法。递归的核心就是:只要当前节点未访问过,就继续访问当前节点的邻居节点们

二、实现

实现代码

实现代码与思路中保持一致

    private HashMap <Node, Node> visited = new HashMap<>();

    public Node cloneGraph(Node node) {
        if (node == null) { // 特殊情况
            return node;
        }
        // 访问过
        if (visited.containsKey(node)) {
            return visited.get(node);
        }
        Node targetNode = new Node(node.val, new ArrayList());
        visited.put(node, targetNode);
        // 遍历邻居节点
        for (Node neighbor: node.neighbors) {
            targetNode.neighbors.add(cloneGraph(neighbor));
        }
        return targetNode;
    }

测试代码

这一题因为测试用例不太好写就没写了,可以用草稿纸代替。

结果

image.png

三、总结

我觉得这一题关键的地方就是以下两点:

  1. 了解连通图,这样才能知道可以通过任意一个节点来还原整个图
  2. 使用哈希表防止重复访问节点,避免堆栈溢出

感谢看到最后,非常荣幸能够帮助到你~♥

如果你觉得我写的还不错的话,不妨给我点个赞吧!如有疑问,也可评论区见~