全排列筛选(java)
蓝桥杯-全排列筛选(java)
蓝桥杯每年必考全排列筛选,一般为填空题;
可以使用for循环暴力破解,但是代码相对较长,也比较乱,不建议使用;
这里使用递归来解决,代码量相对较少,也很好理解;
如下为:0-9的全排列个数;
如需实现从0-9里选n个数只需要改变dfs的参数k的传值就可以了;
全排列模板代码:
public class Main { static int count=0;// 计数器 public static void main(String[] args) { int[] arr = new int []{0,1, 2, 3,4,5,6,7,8,9};//数组元素为需要全排列的数,如果想排列字母改成char数组传入就可以了 dfs(arr, 0, 10);// 改成dfs(arr,0,5)就是从中选5个数全排列,之后输出语句选数组前五个输出即可 System.out.println(count); } // 递归全排列 public static void dfs(int arr[], int num, int k) { if (num == k) {// 递归出口 if (panDuan(arr)) {// 筛选 // 里面可以输出,计数,根据具体情况填写 count++; /* for (int i = 0; i < k; i++){ System.out.print(arr[i]);
}System.out.println(); */
} } for (int i = num; i < arr.length; i++) { swap(arr, num, i); dfs(arr, num + 1, k); swap(arr, num, i); } } // 筛选方法 private static boolean panDuan(int[] arr) {
// 根据题目的条件判断筛选
return false; } // 数组元素交换,注:变量之间不可以用函数交换 public static void swap(int[] arr, int i, int j) { int t = arr[i]; arr[i] = arr[j]; arr[j] = t; } }
例题:
标题:五星填数
如【图1.png】的五星图案节点填上数字:1~12,除去7和11。
每条直线上数字和相等。
如图就是恰当的填法。
请你利用计算机搜索所有可能的填法有多少种。
注意:旋转或镜像后相同的算同一种填法。
注意:这里旋转或镜像:旋转有5种相同状态(旋转360度过程中遇到五次一致的状态),每种状态有2种镜像(二维图形镜像一般都是2种),所以结果要除以10;
public class Demo2 { static int count=0; public static void main(String[] args) { int arr[]=new int[]{1,2,3,4,5,6,8,9,10,12};//除去7,11 dfs(arr,0,10); System.out.println(count/10); } private static void dfs(int[] arr, int num, int k) { // TODO Auto-generated method stub if(num==k){ if(panDuan(arr)){ count++;// 条件达到,count++; } } for(int i=num;i<arr.length;i++){ swap(arr,num,i); dfs(arr,num+1,k); swap(arr,num,i); } } private static void swap(int[] arr, int num, int i) { // TODO Auto-generated method stub int temp=arr[num]; arr[num]=arr[i]; arr[i]=temp; } private static boolean panDuan(int[] arr) { // TODO Auto-generated method stub //判断五条边相等 int a1=arr[0]+arr[2]+arr[5]+arr[8]; int a2=arr[1]+arr[2]+arr[3]+arr[4]; int a3=arr[0]+arr[3]+arr[6]+arr[9]; int a4=arr[1]+arr[7]+arr[5]+arr[9]; int a5=arr[4]+arr[6]+arr[7]+arr[8]; /* 0 1 2 3 4 5 6 7 8 9*/ if(a1==a2&&a2==a3&&a3==a4&&a4==a5){ return true; }else return false; } }
错误或不足的地方欢迎指正!!
最后分享一个喜欢的句子:
其实你我都改变不了什么。萍水相逢,缘开缘灭。