蓝桥杯题目练习 提升篇 DFS [蓝桥杯2016决赛]随意组合

随意组合

题目描述

小明被绑架到X星球的巫师W那里。其时,W正在玩弄两组数据 (2 3 5 8) 和 (1 4 6 7)
他命令小明从一组数据中分别取数与另一组中的数配对,共配成4对(组中的每个数必被用到)。
小明的配法是:{(8,7),(5,6),(3,4),(2,1)}。巫师凝视片刻,突然说这个配法太棒了!
因为:每个配对中的数字组成两位数,求平方和,无论正倒,居然相等:
87^2 + 56^2 + 34^2 + 21^2 = 12302
78^2 + 65^2 + 43^2 + 12^2 = 12302
小明想了想说:“这有什么奇怪呢,我们地球人都知道,随便配配也可以啊!”
{(8,6),(5,4),(3,1),(2,7)}
86^2 + 54^2 + 31^2 + 27^2 = 12002
68^2 + 45^2 + 13^2 + 72^2 = 12002
巫师顿时凌乱了。。。。。
请你计算一下,包括上边给出的两种配法,巫师的两组数据一共有多少种配对方案具有该特征。
配对方案计数时,不考虑配对的出现次序。
就是说:{(8,7),(5,6),(3,4),(2,1)}与{(5,6),(8,7),(3,4),(2,1)}是同一种方案。

输出

输出一个整数表示答案

思路

将两组数据分别保存到a,b两个数组中。 a[] = {2,3,5,8} b[] ={1,4,6,7}
将dfs的参数index指向a数组中的第index个元素,然后遍历b数组中是否有未匹配的元素,有则与a中第index个元素匹配。直接将平方和加到sum1, sum2中。
代码如下:

#include <iostream>
using namespace std;
int a[5]={2,3,5,8};
int b[5]={1,4,6,7};
bool visb[5]; //用来判断b数组中的元素是否被匹配 
int sum1,sum2; //将平方和存储。 
void dfs(int index){
	if(index==4){
	
		if(sum1==sum2){
			sum++;
			return;
		}
		else return;
	}
		for(int j=0;j<4;j++){
			if(!visb[j]){
				visb[j]=true;
				sum1=(a[index]*10+b[j])*(a[index]*10+b[j])+sum1;
				sum2=(a[index]+b[j]*10)*(a[index]+b[j]*10)+sum2;
				dfs(index+1);
				sum1=sum1-(a[index]*10+b[j])*(a[index]*10+b[j]);
				sum2=sum2-(a[index]+b[j]*10)*(a[index]+b[j]*10);
				visb[j]=false;
			}
		}
}
int main() {
	for(int i=0;i<10;i++)
		for(int j=0;j<10;j++){
			ab[i][j]=false;
		}
	sum1=0; sum2=0;
	dfs(0);
	cout<<sum;
	return 0;
}

答案是24. 也就是这两个数组的任意组合都满足条件。

### 关于BFS和DFS算法蓝桥杯竞赛题目 #### 广度优先搜索(BFS) 广度优先搜索是一种用于遍历或搜索树或图结构的算法。该方法从根节点开始,先访问离根最近的所有邻居节点,然后再进入下一层继续这一过程直到遍历结束[^2]。 #### 深度优先搜索(DFS) 深度优先搜索也是一种用于遍历或搜索树或图的方法。不同于广度优先搜索的是,这种方法会尽可能深地沿着每个分支前进,只有当遇到已经访问过的顶点或是死胡同时才会回溯并尝试其他未探索的路径[^1]。 #### 示例代码实现 下面给出一段Python代码来展示如何利用这两种算法解决实际问题: ##### 使用DFS求解全排列问题 ```python N = 10 path = [0] * N state = [False] * N def dfs(u): if u == n: for i in range(n): print(path[i], end=' ') print() return for i in range(n): if not state[i]: path[u] = i + 1 state[i] = True dfs(u + 1) # 处理下一个位置 # 恢复现场 path[u] = 0 state[i] = False n = int(input()) dfs(0) # 从第0个位置开始处理 ``` 这段程序实现了基于DFS的全排列生成器,可以用来作为练习题目的基础框架之一[^3]。 ##### 解决迷宫问题的例子 (假设使用队列实现BFS) ```python from collections import deque maze = [ "########", "#S.....#", "#.######", "#..#.##.", "#...G.#.", "########" ] start, goal = None, None for y in range(len(maze)): for x in range(len(maze[y])): if maze[y][x] == 'S': start = (y,x) elif maze[y][x] == 'G': goal = (y,x) def bfs(): queue = deque([start]) visited = set(start) while queue: pos = queue.popleft() if pos == goal: return True for dy,dx in ((0,-1),(0,+1),(-1,0),(+1,0)): next_pos = (pos[0]+dy,pos[1]+dx) if all([ 0<=next_pos[0]<len(maze), 0<=next_pos[1]<len(maze[next_pos[0]]), maze[next_pos[0]][next_pos[1]] != '#', next_pos not in visited, ]): queue.append(next_pos) visited.add(next_pos) return False print(bfs()) ``` 此段代码展示了怎样运用BFS去查找迷宫中的出路,其中起点标记为'S'而终点则被记作'G'^[2].
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值