UVA 208 Firetruck

来源:互联网 发布:mac上铃声软件 编辑:程序博客网 时间:2024/06/05 01:59

题意:输入一个n个结点的无向图以及某个结点m,按照字典序从小到大顺序输出从结点1到结点m的所有路径,要求结点不能重复经过

解题思路:回溯.裸搜的话会超时,要事先判断结点1是否可以到达结点m,这里是用floyd算法实现的,据说也可以用并查集实现

代码:

#include <iostream>#include <algorithm>#include <cstring>#include <string>#include <cmath>#include <cstdio>using namespace std;#define INF 0x3f3f3f3fint g[30][30],floyd[30][30],d[30],vis[30];int m,cnt,v;void init(){    for(int i=1;i<=21;i++)//初始化    {        for(int j=1;j<=21;j++)        {            g[i][j]=INF;            floyd[i][j]=INF;        }    }}void dfs(int p,int cur){    if(p==m)    {        for(int i=0;i<cur;i++)        {            if(i)printf(" %d",d[i]);            else printf("%d",d[i]);        }        printf("\n");        cnt++;        return ;    }    for(int i=1;i<=v;i++)    {        if(!vis[i]&&g[p][i]==1&&floyd[m][i]!=INF)        {            d[cur]=i;            vis[i]=1;            dfs(i,cur+1);            vis[i]=0;        }    }}int main(){    int cas=0;    while(scanf("%d",&m)==1)    {        init();        cnt=0;        v=0;        int x,y;        while(scanf("%d%d",&x,&y)&&x+y)        {            g[x][y]=g[y][x]=1;            floyd[x][y]=floyd[y][x]=1;            v=max(v,x);            v=max(v,y);        }        for(int k=1;k<=v;k++)//floyd算法        {            for(int i=1;i<=v;i++)            {                for(int j=1;j<=v;j++)                {                    floyd[i][j]=min(floyd[i][j],floyd[i][k]+floyd[k][j]);                }            }        }        memset(vis,0,sizeof(vis));        vis[1]=1;        d[0]=1;        printf("CASE %d:\n",++cas);        dfs(1,1);        printf("There are %d routes from the firestation to streetcorner %d.\n",cnt,m);    }    return 0;}