LeetCode – Clone Graph (Java)

Clone an undirected graph. Each node in the graph contains a label and a list of its neighbors.

Java Solution 1 - DFS

HashMap<Node, Node> map = new HashMap<>();
public Node cloneGraph(Node node) {
    map.put(node, new Node(node.val, new ArrayList<>()));
    for(Node neighbor: node.neighbors){
    return map.get(node);

Java Solution 2 - BFS

public Node cloneGraph(Node node) {
    Map<Node, Node> map = new HashMap<>();
    Queue<Node> queue = new ArrayDeque<>();
    map.put(node, new Node(node.val, new ArrayList<>()));
    while (!queue.isEmpty()) {
        Node h = queue.poll();
        for (Node neighbor : h.neighbors) {
            if (!map.containsKey(neighbor)) {
                map.put(neighbor, new Node(neighbor.val, new ArrayList<>()));
    return map.get(node);
Category >> Algorithms  
If you want someone to read your code, please put the code inside <pre><code> and </code></pre> tags. For example:
String foo = "bar";
  • deepak shinde

    The Time complexity for cloning the graph is O(V+E) and thats because we
    shall be traversing each vertex of the graph from the Queue and then
    visiting each edge E atleast once.

  • Rishabh Jain

    What would be the time complexity?

  • Milan

    A DFS with alreadyAvailable map that stores (label,new node)
    And if node is present in map, use it else create a new node and put in map.

    public UndirectedGraphNode cloneGraph(UndirectedGraphNode node) {
    if (node == null)
    return node;
    Map alreadyAvailable = new HashMap();
    return cloneGraphHelper(node,alreadyAvailable);
    private UndirectedGraphNode cloneGraphHelper(UndirectedGraphNode node, Map alreadyAvailable) {
    if ( alreadyAvailable.containsKey(node.label) )
    return alreadyAvailable.get(node.label);
    UndirectedGraphNode returnNode = new UndirectedGraphNode(node.label);
    for(UndirectedGraphNode N: node.neighbors)
    return returnNode;

  • gowtham Bk

    Why should it be bfs ? why not dfs??

  • rashmibrahma

    import java.util.HashSet;

    import java.util.Set;

    public class CloneGraph {

    public static UndirectedGraphNode cloneGraph(UndirectedGraphNode root1) {


    return null;


    UndirectedGraphNode root2;

    Set visited=new HashSet();

    root2=cloneGraph(root1, visited);

    return root2;


    private static UndirectedGraphNode cloneGraph(UndirectedGraphNode root1, Set visited){


    UndirectedGraphNode root2=new UndirectedGraphNode(root1.label);

    for(UndirectedGraphNode node:root1.neighbors){



    cloneGraph(node, visited);



    return root2;



  • Wayne

    import java.util.ArrayList;

    import java.util.HashMap;

    import java.util.List;

    public class Solution {

    public UndirectedGraphNode cloneGraph(UndirectedGraphNode node) {

    if (node == null) {

    return null;


    HashMap hasProcessed

    = new HashMap();

    return cloneGraph(node, hasProcessed);


    private UndirectedGraphNode cloneGraph(UndirectedGraphNode node,

    HashMap hasProcessed) {

    UndirectedGraphNode newNode = new UndirectedGraphNode(node.label);

    hasProcessed.put(node, newNode);

    for (UndirectedGraphNode next : node.neighbors) {

    if (hasProcessed.get(next) == null) {

    newNode.neighbors.add(cloneGraph(next, hasProcessed));

    } else {




    return newNode;



  • Howard

    Great code. I just wonder whether it should be queue.poll( ), instead of queue.pop( )?

  • Yoonsoo Kim

    How about the following algorithm in C++? I don’t think we need to use BFS when copying a whole graph. A whole graph can’t be represented by a single node but by a list of node. So I think the following approach works too. The most important thing to clone a whole graph is using hash map between original node and cloned node, not the BFS.

    struct node {
    int v;
    vector E;
    node(int v) : v(v) {}

    auto clone_graph = [](const vector& G) {
    vector retG(G.size(), nullptr);
    unordered_map node_map;
    for (size_t i = 0; i v };
    node_map[G[i]] = retG[i];

    for (size_t i = 0; i < retG.size(); ++i) {
    for (size_t j = 0; j E.size(); ++j) {
    retG[i]->E[j] = node_map[G[i]->E[j]];

    return retG;

    Here is another approach which is using BFS.

    auto clone_graph2 = [](const vector& G) {
    unordered_map cloned;
    function impl = [&](node* o) {
    queue q;
    cloned[o] = new node(o->v);

    while (!q.empty()) {
    auto n = q.front();
    for (size_t i = 0; i E.size(); ++i) {
    if (cloned.find(n->E[i]) == cloned.end()) {
    cloned[n->E[i]] = new node(n->E[i]->v);
    cloned[n]->E[i] = cloned[n->E[i]];

    return cloned[o];

    vector retG(G.size(), nullptr);
    for (size_t i = 0; i < retG.size(); ++i) {
    retG[i] = cloned.find(G[i]) == cloned.end() ? impl(G[i]) : cloned[G[i]];

    return retG;

    I prefer the first approach for its simplicity

  • ryanlr

    Thanks for your comment. I want to read your code, can you put your code inside <pre></pre> tags?

  • Henry

    Thanks X Wang!

    I used a modified depth first search


    * Definition for undirected graph.

    * class UndirectedGraphNode {

    * int label;

    * List neighbors;

    * UndirectedGraphNode(int x) { label = x; neighbors = new ArrayList(); }

    * };


    public class Solution {

    private Map marked = new HashMap();

    public UndirectedGraphNode cloneGraph(UndirectedGraphNode node) {

    if (node==null) return null;

    UndirectedGraphNode result = new UndirectedGraphNode(node.label);

    marked.put(node.label, result);

    for (int i=0; i<node.neighbors.size(); i++) {

    UndirectedGraphNode toClone = node.neighbors.get(i);

    UndirectedGraphNode neighbor;

    if (!marked.containsKey(toClone.label)) {

    neighbor = cloneGraph(toClone);

    } else { neighbor = marked.get(toClone.label); }



    return result;