uva10054

题意:给你n个珠子,一个珠子分为两半有两种颜色,用1到50来表示50种不同的颜色。把这些珠子串起来,两个紧挨着的珠子要满足一个条件就是接触的那部分颜色要相同

例如(1,2)(2,4),两个珠子的接触部分颜色相同都为2。当然,因为珠子最后是连成环的,第一个珠子和最后一个珠子也会接触,也要买满足这个条件

先输入T,有T组数据

输入n,有n个珠子

下面n行每行两个数字表示这个珠子的两个颜色,然后问你能不能连成一条链,能的话输出任意一种连接情况即可,不能的话输出失败

 

其本质是欧拉回路,欧拉回路的题只做过每背景的裸题,第一次做这个,想不到是欧拉回路,然后想了差不多一个小时才想到是欧拉回路,说说思考的思路

其实1到50代表50钟颜色也就是50个点,一个珠子的信息例如(1,2)其实就是一个无向边(1,2),注意是无向边,因为珠子是可以转过来的,(1,2)=(2,1),那么无疑就可以建立一个图了

另外,给你的n个珠子如果是能连成链的话,那么其实任意一个珠子都可以作为起点,最后要回到自己,然后就想到,那不就是在已有的图中进行遍历,遍历了所有的点然后回到自己吗?怎么那么像那么欧拉的………………然后再思考了一些细节,稍微推理了一下确定了就是要判断是否存在欧拉回路,若存在即输出路径

 

无向图的欧拉回路判断和路径输出

1.判断所有的点的度是否为偶数,如果有点不为偶数,则不存在欧拉回路

2.满足1的条件下,判断所给的图是否连通,不连通也不是欧拉回路

3.满足1和2的就是欧拉回路,然后dfs逆序输出路径,主要一定要逆序,不逆序是错的,后面会解释

 

经过有意的测试那先这道题是不需要判断图连通的,也就是所给数据图一定是连通的,所以直接判断度即可

先给出代码,在详细分析

#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;

const int maxn=100;
int  du[maxn],tu[maxn][maxn];
int n;

void print(int u){
     for (int i=1;i<=50;i++){
        if(tu[u][i]){
            tu[u][i]--;
            tu[i][u]--;
            print(i);
            printf("%d %d\n",i,u);
        }
     }
}
int  main(){
    int t;
    int cas=0;
    int u,v;
    scanf("%d",&t);
    while(t--){
        memset(tu,0,sizeof(tu));
        memset(du,0,sizeof(du));
        if(cas) printf("\n");
        printf("Case #%d\n",++cas);
        scanf("%d",&n);
        for (int i=1;i<=n;i++){
            scanf("%d %d",&u,&v);
            du[u]++;
            du[v]++;
            tu[u][v]++;
            tu[v][u]++;
        }
        int j;
        for (j=1;j<=50;j++){
            if(du[j]%2) break;
        }
        if(j<=50) printf("some beads may be lost\n");
        else {
            for (int i=1;i<=50;i++)
                print(i);
        }
    }
return 0;
}

posted @ 2018-01-02 19:02  lmjer  阅读(194)  评论(0编辑  收藏  举报