码迷,mamicode.com
首页 > 其他好文 > 详细

LeetCode OJ 133题:Clone Graph

时间:2015-03-30 20:39:14      阅读:159      评论:0      收藏:0      [点我收藏+]

标签:

题目如下:

技术分享

题目挺长的,其实只需要关注第一行就OK了。这道题思路挺明显的,对于图来说要么BFS,要么DFS,至于具体细节,我觉得与138题:Copy List with Random Pointer很像。在BFS或DFS过程中,可能要调整顶点的邻接点,这个时候不要忘了它的邻接点可能还没有创建。所以,有以下思路:

遍历两遍无向图。第一遍,创建所有结点,不用保存顶点间关系。第二遍,调整顶点间关系。顶点间关系保存在neighbors中,为了能够找到新创建顶点的位置,第一遍遍历时候需要保存原顶点与新顶点指针的一一对应关系,这里可用map或unordered_map保存。

这里我说的有点啰嗦,请看代码中注释就明白了。这里,我采用BFS遍历。时间复杂度为O(N),空间复杂度也为O(N)。

 1 /**
 2  * Definition for undirected graph.
 3  * struct UndirectedGraphNode {
 4  *     int label;
 5  *     vector<UndirectedGraphNode *> neighbors;
 6  *     UndirectedGraphNode(int x) : label(x) {};
 7  * };
 8  */
 9 class Solution {
10 public:
11     UndirectedGraphNode* cloneGraph(UndirectedGraphNode *node)
12     {
13         if (node == NULL)
14         {
15             return NULL;
16         }
17     
18         map<UndirectedGraphNode*, UndirectedGraphNode*> gphMap;
19         queue<UndirectedGraphNode*> gphQue;
20         
21         //创建所有顶点
22         gphQue.push(node);
23         while (!gphQue.empty())
24         {
25             UndirectedGraphNode *tmp = gphQue.front();
26             gphQue.pop();
27     
28             if (gphMap.find(tmp) == gphMap.end())
29             {
30                 UndirectedGraphNode *newNode = new UndirectedGraphNode(tmp->label);
31                 gphMap[tmp] = newNode;
32     
33                 for (int i = 0; i != tmp->neighbors.size(); ++i)
34                 {
35                     gphQue.push(tmp->neighbors[i]);
36                 }
37             }
38         }
39     
40         //调整顶点间关系
41         gphQue.push(node);
42         while (!gphQue.empty())
43         {
44             UndirectedGraphNode *tmp = gphQue.front();
45             gphQue.pop();
46     
47             UndirectedGraphNode *exitNode = gphMap[tmp];
48             if (exitNode->neighbors.empty() && !tmp->neighbors.empty())
49             {
50                 for (int i = 0; i != tmp->neighbors.size(); ++i)
51                 {
52                     exitNode->neighbors.push_back(gphMap[tmp->neighbors[i]]);
53                     gphQue.push(tmp->neighbors[i]);
54                 }
55             }
56         }
57     
58         return gphMap[node];
59     }
60 };

其实上面这种方法,是挺清楚直观的。但还是要考虑一下,能不能优化一下,只遍历一次。反正,我参加面试时,面试官说:”只遍历一次,找出(实现)…。其实,实现起来并不难,只需要把两部分遍历的操作合并起来就好了。下面我分别给出BFS和DFS算法,两种算法的时间复杂度都是O(N),空间复杂度也都是O(N)。

实现图拷贝的BFS算法如下:

 1 class Solution {
 2 public:
 3     UndirectedGraphNode *cloneGraph(const UndirectedGraphNode *node) 
 4     {
 5         if (node == NULL) 
 6         {
 7             return NULL;
 8         }
 9 
10         map<const UndirectedGraphNode*, UndirectedGraphNode*> gphMap;
11         queue<const UndirectedGraphNode *> gphQue;
12         
13         gphQue.push(node);
14         gphMap[node] = new UndirectedGraphNode(node->label);
15         while (!gphQue.empty()) 
16         {
17             const UndirectedGraphNode *tmp = gphQue.front();
18             gphQue.pop();
19 
20             for (int i = 0; i != tmp->neighbors.size(); ++i)
21             {
22                 if (gphMap.find(tmp->neighbors[i]) == gphMap.end())
23                 {
24                     //build the vertex
25                     UndirectedGraphNode *newNode = new UndirectedGraphNode(tmp->neighbors[i]->label);
26                     gphMap[tmp->neighbors[i]] = newNode;
27                     gphMap[tmp]->neighbors.push_back(newNode);            //Adjust the Vertex    
28                     gphQue.push(tmp->neighbors[i]);
29                 }
30                 else
31                 {
32                     gphMap[tmp]->neighbors.push_back(gphMap[tmp->neighbors[i]]);
33                 }
34             }
35         }
36 
37         return gphMap[node];
38     }
39 };

 

实现图拷贝的DFS算法如下:

 1 class Solution {
 2 public:
 3     UndirectedGraphNode *cloneGraph(const UndirectedGraphNode *node) 
 4     {
 5         if(node == NULL)
 6         {
 7             return NULL;
 8         }
 9     
10         map<const UndirectedGraphNode*, UndirectedGraphNode*> gphMap;
11         
12         return GphClone(node, gphMap); //or return gphMap[node]
13     }
14 private:
15     // DFS
16     static UndirectedGraphNode* GphClone(const UndirectedGraphNode *node, 
17         map<const UndirectedGraphNode*, UndirectedGraphNode*> &gphMap) 
18     {
19             // a copy already exists
20             if (gphMap.find(node) != gphMap.end()) 
21             {
22                 return gphMap[node];                
23             }
24 
25             UndirectedGraphNode *newNode = new UndirectedGraphNode(node->label);
26             gphMap[node] = newNode;
27 
28             for (int i = 0; i != node->neighbors.size(); ++i)
29             {
30                 newNode->neighbors.push_back(GphClone(node->neighbors[i], gphMap));
31             }
32             
33             return newNode;
34     }
35 };

 虽然时间复杂度都是O(N),但从提交结果看,DFS好像快一点,这个不懂。

LeetCode OJ 133题:Clone Graph

标签:

原文地址:http://www.cnblogs.com/mengwang024/p/4378838.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!