【蓝桥杯】A,2,3,4,5,6,7,8,9 共9张纸牌排成一个正三角形(A按1计算)。要求每个边的和相等。下图就是一种排法(如有对齐问题,参看p1.png)。 A 9 6 48 3 7 5 2这

A,2,3,4,5,6,7,8,9 共9张纸牌排成一个正三角形(A按1计算)。要求每个边的和相等。
下图就是一种排法(如有对齐问题,参看p1.png)。
 
      A
     9 6
    4   8
   3 7 5 2
 
这样的排法可能会有很多。
 
如果考虑旋转、镜像后相同的算同一种,一共有多少种不同的排法呢?
 
请你计算并提交该数字。
 
注意:需要提交的是一个整数,不要提交任何多余内容。
 

代码如下:

public class Main{

	static int count=0;
    static boolean bool[]=new boolean[10];
    static int num[]=new int[10];
	public static void main(String[] args) {
        dfs(1);
        System.out.println(count/3/2);
	}
    public static void dfs(int step) {
    	if(step==10) {
    		if(num[1]+num[2]+num[4]+num[6]==num[6]+num[7]+num[8]+num[9]
    				&&num[1]+num[2]+num[4]+num[6]==num[1]+num[3]+num[5]+num[9]) {
    			count++;
    		}
    		return;
    	}
    	for(int i=1;i<10;i++) {
    		if(!bool[i]) {
    			bool[i]=true;
    			num[step]=i;
    			dfs(step+1);
    			bool[i]=false;
    		}
    	}
    }
}

 答案:144

回溯案例如下图所示:

解释:首先,让我们明确代码的功能:这是一个深度优先搜索(DFS)算法。条件是数组 num 中的前四个数字(1、2、4、6位)的和必须等于接下来的四个数字(6、7、8、9位)的和,同时也必须等于另一组四个数字(1、3、5、9位)的和。

下面是每一步的详细解释:

  1. 初始化

    • count:初始化为0,用于记录满足条件的排列数量。
    • bool[]:一个长度为10的布尔数组,初始值全部为false,用于标记数字是否已经被使用。
    • num[]:一个长度为10的整数数组,用于存储当前排列的数字。
  2. 主函数开始

    • 调用 dfs(1) 开始深度优先搜索。
  3. 进入 dfs(1)

    • step:当前为1,表示正在填充 num 数组的第一个位置。
  4. 开始循环(第一次循环,i=1)

    • bool[1]:之前是false,现在设置为true,表示数字1已被使用。
    • num[1]:设置为1。
    • 递归调用 dfs(2)
  5. 进入 dfs(2)

    • step:现在为2,表示正在填充 num 数组的第二个位置。
    • 循环中,i 从1遍历到9,但1已经被使用(bool[1] 为true),所以跳过1。
    • 当 i 为2时,因为2还未被使用,所以 bool[2] 设置为true,num[2] 设置为2,然后递归调用 dfs(3)
  6. 进入 dfs(3),以此类推,直到 dfs(10)

  7. 到达 dfs(10)

    • 此时,num[] 数组已被完全填充。
    • 检查条件是否满足:num[1]+num[2]+num[4]+num[6] 是否等于 num[6]+num[7]+num[8]+num[9] 以及 num[1]+num[2]+num[4]+num[6] 是否等于 num[1]+num[3]+num[5]+num[9]
    • 如果条件满足,count 增加1。
  8. 回溯

    • 从 dfs(10) 返回,bool[9] 被设置为false,因为9在当前的排列中已被使用,但在其他可能的排列中可能还需要使用。
    • 类似地,dfs(9) 返回,bool[8] 被设置为false,依此类推,直到最初的 dfs(1) 返回。
  9. 主函数结束

    • 打印 count 的值,即满足条件的排列数量。

需要注意的是,在每次递归调用 dfs(step+1) 后,都会通过 bool[i]=false 进行回溯,这是深度优先搜索中常见的做法,用于撤销当前的选择,以便尝试其他可能性。

  • 8
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值