月赛最后一题答案

本文介绍了一种使用广度优先搜索(BFS)算法解决密码矩阵问题的方法。该方法通过将3x3数字矩阵视为状态空间,实现了从任意初始状态到目标状态(如123456789)的有效路径查找。文中详细展示了如何实现矩阵的状态转换、搜索过程的限制条件及最终解决方案。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

#include<bits/stdc++.h>
using namespace std;
int num[6][6];
map<int,int>m;
struct node{
	int num;
	int step;
};
void build(int temp){
	memset(num,0,sizeof(num));
	for(int i=3;i>=1;i--){
		for(int j=3;j>=1;j--){
			num[i][j]=temp%10;
			temp/=10;
		}
	}
}
int change(int k){
	int n,dir;
	if(k<=6){//k<6让行改变 
		n=(k+1)/2;dir=(k%2);
		if(dir==1){
			num[n][0]=num[n][3];
			for(int i=3;i>=1;i--)num[n][i]=num[n][i-1];
		}
		else{
			num[n][4]=num[n][1];
			for(int i=1;i<=3;i++)num[n][i]=num[n][i+1];
		}
	}
	if(k>6){//k>6让列改变 
		n=(k+1-6)/2;dir=(k%2);
		if(dir==1){
			num[0][n]=num[3][n];
			for(int i=3;i>=1;i--)num[i][n]=num[i-1][n];
		}
		else{
			num[4][n]=num[1][n];
			for(int i=1;i<=3;i++)num[i][n]=num[i+1][n];
		}
	}
	int temp=0;
	for(int i=1;i<=3;i++)for(int j=1;j<=3;j++)temp=temp*10+num[i][j];//从新把密码矩阵压缩成数字并返回回去 
	return temp;
}
void bfs(int temp){
	queue<node>q;
	while(!q.empty())q.pop();
	node t;
	t.num=temp;t.step=0;
	q.push(t);
	while(!q.empty()){
		node now=q.front();
		q.pop();
		for(int i=1;i<=12;i++){//判断12个方向 
			node next;
			build(now.num);
			next.num=change(i);
			next.step=now.step+1;
			if(!m.count(next.num) && next.step<=5){//如果next.num没有在映射里面出现过,并且还可以继续搜就继续 
				m[next.num]=now.step+1;
				q.push(next);
			}
		}
	}
}
int main(){
	int test;
	scanf("%d",&test);
	while(test--){
		m.clear();//清空映射 (有兴趣可自行百度映射怎么用) 
		int ok=0;
		int temp=0;
		scanf("%d",&temp);
		build(temp);//把数字还原到密码矩阵里 
		m[temp]=0;
		if(m.count(123456789)){//判断数字123456789是否在映射里出现过 
			printf("0\n");
			continue;
		}
		else bfs(temp);//广搜 
		if(m.count(123456789))printf("%d\n",m[123456789]);
		else printf("impossible\n");
	}
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值