多米诺 ——一种用木头或者其他材料做的小方块进行的游戏,其中每个小方块面上通常标记点数或分数。这些小方块被称作骨牌,多米诺。有时用骨片,用人,甚至用卡片。
每个小块的表面被一条线分割成两部分,每一部分都写上了可能成对的号码。
在差不多所有的现代多米诺骨牌游戏中,比赛原则是要使两个标有相同或成对的号码的小方块首尾相接应。
——《大英百科全书》
给你一些多米诺骨牌,每块的两部分都标记上 0 到 6 的号码,你的任务是把这些骨牌排列在一条直线上,使得相邻骨牌的相邻部分有同样的号码。骨牌可以左右翻转。
输入
第一行包括一个整数 N (1 ≤ N ≤ 100) 表示骨牌总数。接下来 N 行描述每一块骨牌两部分的号码,每行两个 0 - 6 的数,用空格隔开。
输出
如果不存在这样的方案,输出 “No solution”。如果方案存在,输出任意一种符合要求的方案。输出方案时应该从左到右描述骨牌的排列,每行输出用空格隔开的一个整数和一个字符,分别表示骨牌的编号和是否翻转骨牌,(+表示不翻转,-表示翻转)。
样例输入
5
1 2
2 4
2 4
6 4
2 1
样例输出
2 -
5 +
1 +
3 +
4 -
#include <cstdio> int n; int a[7][7]; struct node{ int x,y; }e[210],d[210]; int deg[210]; int tot; int cnt; int st; int dfs(int x){ for (int i=0;i<7;i++){ if (a[x][i]){ a[x][i]--;//删边 a[i][x]--; dfs(i); tot++;//记录答案 d[tot].x=x; d[tot].y=i; } } } int main(){ scanf("%d",&n); for (int i=1;i<=n;i++){ int x,y; scanf("%d%d",&x,&y); e[i].x=x;//记录边便于输出比较 e[i].y=y; deg[x]++;//存入度 deg[y]++; a[x][y]++;//矩阵存边 a[y][x]++; } cnt=0; for (int i=0;i<7;i++){//随意找到一个可行的起点 if (deg[i]){ st=i; break; } } for (int i=0;i<7;i++){//记录入度为奇数的点的个数 if ((deg[i] & 1)==1){ st=i; cnt++; } } if (cnt!=0 && cnt!=2){//不满足欧拉路的性质 --只有0个或2个入度为奇数的点的图是欧拉图 printf("No solution\n"); return 0; } dfs(st);//遍历过程 if (tot<n){//不能完全遍历 printf("No solution\n"); return 0; } for (int i=tot;i>0;i--){//模拟输出 for (int j=1;j<=n;j++){ if (e[j].x==d[i].x && e[j].y==d[i].y){ printf("%d +\n",j); e[j].x=-1; break; }else if (e[j].y==d[i].x && e[j].x==d[i].y){ printf("%d -\n",j); e[j].x=-1; break; } } } return 0; }