UVA 247 - Calling Circles(floyd判断包闭 ,dfs输出)

来源:互联网 发布:在线c语言编译器 编辑:程序博客网 时间:2024/06/16 12:29

紫书推荐的题

题意:

  给你n个人,m条边,a->b,b->a,才能说这两个人是联通的。问现在有多少个联通圈。输出每个联通圈。n<=25

思路:

  直接建图,用有向图的闭包传递特性来处理每个人之间的联通关系。然后dfs一次,遍历邻接矩阵中与某个点相连的几个点,边遍历, 边打印输出。

代码:

#include <iostream>#include <cstdio>#include <algorithm>#include <cstring>#include <vector>#include <map>#include<string>using  namespace std;const int N=26;int  n,m;int d[N][N],id;int vis[N];map<string,int>name;vector<string>Name;void init(){  name.clear();  Name.clear();  id=0;  memset(d, 0, sizeof(d));  memset(vis, 0, sizeof(vis));}void dfs(int u){  vis[u]=1;  for(int v=0; v<n; v++){    if(!vis[v] && d[u][v] && d[v][u]){      cout<<", "<<Name[v];      dfs(v);    }  }}int  main(){  int kase=1;  while(cin>>n>>m){    init();    if(!n && !m)break;    for(int i=0; i<m; i++){      string s1,s2;      cin>>s1>>s2;      if(!name.count(s1)){        name[s1] = id++;        Name.push_back(s1);      }      if(!name.count(s2)){        name[s2] = id++;        Name.push_back(s2);      }      int x = name[s1] , y = name[s2];  /*找出2个字符串对应的ID*/      d[x][y]=1;    /*连接*/    }    for(int k=0; k<n; k++)      for(int i=0; i<n; i++)        for(int j=0; j<n; j++)          d[i][j]=d[i][j]||(d[i][k] && d[k][j]);    if(kase>1)cout<<endl;    cout << "Calling circles for data set " << kase++ <<":" << endl;    for(int i=0; i<n; i++){      if(!vis[i]){        cout<<Name[i];        dfs(i);        cout<<endl;      }    }  }  return 0;}/*5 5A BA BA BC DE C*/


0 0
原创粉丝点击