版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/scylhy/article/details/87864965
133. 克隆图-M
克隆一张无向图,图中的每个节点包含一个 label (标签)和一个 neighbors (邻接点)列表 。
OJ的无向图序列化:
节点被唯一标记。
我们用 # 作为每个节点的分隔符,用 , 作为节点标签和邻接点的分隔符。
例如,序列化无向图 {0,1,2#1,2#2,2}。
该图总共有三个节点, 被两个分隔符 # 分为三部分。
第一个节点的标签为 0,存在从节点 0 到节点 1 和节点 2 的两条边。
第二个节点的标签为 1,存在从节点 1 到节点 2 的一条边。
第三个节点的标签为 2,存在从节点 2 到节点 2 (本身) 的一条边,从而形成自环。
我们将图形可视化如下:
1
/ \
/ \
0 --- 2
/ \
\_/
-
分析
这道题目的意思是,复制输入图到内存中,并且,需要遍历,应该会检测对应的地址,直接复制是不行的。
挺讨厌这道题的,既不给测试样例,表达还不清晰,还有多重环,反复的都算,并且node标签有可能是负数,这样你就必须得用map。
图遍历,无非就两种,dfs和bfs。 -
code1:dfs&bfs
#include<iostream>
#include<vector>
#include<map>
using namespace std;
struct UndirectedGraphNode {
int label;
vector<UndirectedGraphNode *> neighbors;
UndirectedGraphNode(int x) : label(x) {};
};
class Solution {
public:
UndirectedGraphNode *cloneGraph(UndirectedGraphNode *node) {
if(node==NULL){
return node;
}
return bfs(node);
return dfs(node);
}
map<int,UndirectedGraphNode*>objs;//存到map中,方便构建后续的相邻关系
UndirectedGraphNode *dfs(UndirectedGraphNode *node) {
if(objs[node->label]!=0){
return objs[node->label];
//dfs从最低返回相连对象,用于构建连接,所以这个是必须的,
//最近树做的少了,优点生疏;深度搜索首先就是要明确要返回什么
}
objs[node->label]=new UndirectedGraphNode(node->label);//只复制个node中label,其他都没复制
for(int i=0;i<node->neighbors.size();i++){
UndirectedGraphNode*ng=dfs(node->neighbors[i]);
objs[node->label]->neighbors.push_back(ng);
//不必担心重复构建边,因为题目的无向边,也是随意的可能0-1,1不到0
//他的数据,是按照上述说的{0,1,2#1,2#2,2}来的
}
return objs[node->label];
}
UndirectedGraphNode *bfs(UndirectedGraphNode *node) {
objs[node->label]=new UndirectedGraphNode(node->label);
queue<UndirectedGraphNode*> q;
q.push(node);
while(q.size()>0){//注意,遍历要按原树的结构进行,切勿跑到新创建的树上
UndirectedGraphNode* p=q.front();
q.pop();
for(int i=0;i<p->neighbors.size();i++){
if(objs[p->neighbors[i]->label]==0){
objs[p->neighbors[i]->label]=new UndirectedGraphNode(p->neighbors[i]->label);
q.push(p->neighbors[i]);
}
objs[p->label]->neighbors.push_back(objs[p->neighbors[i]->label]);
}
}
return objs[node->label];
}
};
int main(){
UndirectedGraphNode*a=new UndirectedGraphNode(0);
UndirectedGraphNode*b=new UndirectedGraphNode(1);
UndirectedGraphNode*c=new UndirectedGraphNode(2);
a->neighbors.push_back(b);
a->neighbors.push_back(a);
a->neighbors.push_back(c);
b->neighbors.push_back(c);
b->neighbors.push_back(a);
c->neighbors.push_back(a);
c->neighbors.push_back(b);
Solution s;
UndirectedGraphNode* d=s.cloneGraph(a);
cout<<"output:"<<endl;
for(map<int,UndirectedGraphNode*>::iterator it=s.objs.begin();it!=s.objs.end();it++){
cout<<it->second->label<<":"<<endl;
for(int j=0;j<it->second->neighbors.size();j++){
cout<<"\t"<<it->second->neighbors[j]->label<<endl;
}
}
return 0;
}
/*测试输出
output:
0:
1
0
2
1:
2
0
2:
0
1
*/