郊游

/*
 * 幼儿园小朋友下周要郊游。带队老师想在郊游时让两名学生组成一个小队进行活动。不过让两名不是朋友
 * 的学生组成一队会发生争执或者不理睬。因此,必须由两名朋友关系的学生组队。
 * 给定各学生的朋友关系详情,编写程序计算出所有可配对的不同方法。任何一个不相同的配对都将视为一种不同的
 * 配对方法。例如以下两种配对方法就属于不同的配对方法。
 * (泰妍,杰西卡)(珊妮,蒂芬妮)(孝渊,余利)
 * (泰妍,杰西卡)(珊妮,余利)(孝渊,蒂芬妮)
 * 
 * 限定时间及内存使用
 *    执行程序的限定时间为1s,内存使用限制为64MB
 * 输入:
 *    输入方式为,第一行输入测试用例个数C(C≤50),各测试用例的第一行输入学生数量n(2≤n≤10)和
 *    朋友关系数m(0≤m≤n(n-1)/2)。下一行输入m个整数对,表示具有朋友关系的学生序号。
 *    序号是0到n-1的整数,相同配对只输入一次。学生数量是双数。	
 * 输出:
 *    每个测试用例用1行输出朋友关系的学生可配成对的总数。
 * 示例输入值:
 * 3
 * 2 1
 * 0 1
 * 4 6
 * 0 1 1 2 2 3 3 0 0 2 1 3
 * 6 10
 * 0 1 0 2 1 2 1 3 1 4 2 3 2 4 3 4 3 5 4 5
 * 示例输出值:
 * 1
 * 3
 * 4
 * 第一个输入(2 1)中,只有两名学生,而且是朋友关系。故只有一种可能,即学生0和学生1。
 * 第二个输入(4 6)中,有4名学生,而且彼此都是朋友。假设各自为丁丁、迪西、娜娜、小波,那么有一下3种组合
 * (丁丁,迪西)(娜娜,小波)
 * (迪西,小波)(娜娜,丁丁)
 * (娜娜,迪西)(小波,丁丁)
 * 
 */
import java.util.Scanner;

public class test1 {
	static int n, m;
	static boolean[][] arefriends = new boolean[10][10];
	static boolean[] books = new boolean[10];

	public static void main(String[] args) {
		Scanner cin = new Scanner(System.in);
		int c = cin.nextInt();
		for (int i = 0; i < c; ++i) {
			n = cin.nextInt();
			m = cin.nextInt();
			if (Check()) {
				if (n == 2 && m == 1) {
					System.out.println(1);
					continue;
				}
				// 避免上一次影响,每次用之前清空数组
				clearAreFriends();// Arrays.fill只能赋值一维数组
				for (int j = 0; j < m; ++j) {
					int x = cin.nextInt();
					int y = cin.nextInt();
					arefriends[x][y] = arefriends[y][x] = true;
				}
				System.out.println(partings());
			} else {
				--i;
			}
		}
		cin.close();
	}

	public static void clearAreFriends() {
		for (int i = 0; i < arefriends.length; ++i) {
			for (int j = 0; j < arefriends[0].length; ++j) {
				arefriends[i][j] = false;
			}
		}
	}

	public static boolean Check() {
		if (n > 0 && n != 1) {// 题目限定了2≤n≤10,虽说多余,但测试用例有n为0的情况
			return true;
		}
		return false;
	}

	// 若第books[i]=i个学生找到了伙伴,则返回true
	public static int partings() {
		// 在剩余学生中查找序号最靠前的学生
		int flag = -1;
		for (int i = 0; i < n; ++i) {
			if (!books[i]) {
				flag = i;
				break;
			}
		}
		// 初始部分:所有学生都找到了伙伴,那么已找出1种组合方式,故终止
		if (flag == -1)
			return 1;
		int res = 0;
		// 选择与此学生组队的伙伴
		for (int end = flag + 1; end < n; ++end) {
			if (!books[end] && arefriends[flag][end]) {
				books[flag] = books[end] = true;
				res += partings();
				books[flag] = books[end] = false;
			}
		}
		return res;
	}
}
========================================Talk is cheap, show me the code=======================================
posted @ 2018-02-27 14:49  绿叶萌飞  阅读(140)  评论(0编辑  收藏  举报