热门智力题 过桥问题和倒水问题)
1. 过桥问题
在漆黑的夜里,四位旅行者来到了一座狭窄而且没有护栏的桥边。如果不借助手电筒的话,大家是无论如何也不敢过桥去的。不幸的是,四个人一共只带了一只手电筒,而桥窄得只够让两个人同时通过。如果各自单独过桥的话,四人所需要的时间分别是1,2,5,8分钟;而如果两人同时过桥,所需要的时间就是走得比较慢的那个人单独行动时所需的时间。问题是,你如何设计一个方案,让用的时间最少。
思路梳理
能者多劳:要么是最快者将最慢的2个送过桥,要么是最快的2个将最慢的2个送过桥。
即将过桥的人按其过桥的时间从小到大排列,设为A,B,…… Y,Z。其中A和B是最快的二个,Y和Z是最慢的二个。
- 将所有旅行者的过桥时间,从小到大排列;
- 循环遍历数组元素,设置条件 —— 最小者将最大2个送走或最小2个将最大2个送走,累加时间和;
- 输出结果。
for (i = n - 1; i > 2; i = i - 2)
{
//最小者将最大2个送走或最小2个将最大2个送走
if (a[0] + a[1] + a[1] + a[i] < a[0] + a[0] + a[i - 1] + a[i])
sum = sum + a[0] + a[1] + a[1] + a[i];
else
sum = sum + a[0] + a[0] + a[i - 1] + a[i];
}
2. 倒水问题
给你一个容量为5升的桶和一个容量为3升的桶,水不限使用,要求精确得到4升水。
思路梳理
解法肯定有很多,可以用宽度优先搜索(BFS),也可以用穷举法。
穷举法实现比较方便,其基本思想是用:用小桶容量的倍数对大桶的容量进行取余。比如3升的桶和5升的桶得到4升水可以这样做:
3 % 5 = 3
6 % 5 = 1
9 % 5 = 4
成功得到4升水。
总结:不断用小桶装水倒入大桶,大桶满了立即清空,每次判断,两个桶中水的容量是否等于指定容量。
这里只是给出一个可行的倒水方案,不一定是最优解。另外倒水问题要注意下像用2升的桶和4升的桶得到3升水这种不可解的情况,这种不可解情况在用本文中对倒水问题所总结的基本思想计算时会得到循环数列。其根本原因是二个桶容量的最大公约数无法被目标容量所整除,如6升的桶和9升的桶无法得到2升水是因为6和9的最大公约数是3即GCD(6,9)=3而3无法整除2。
回溯法搜索解空间树时,通常采用两种策略避免无效搜索,一种是用约束函数法在节点处剪去不符合要求的子树;第二种是用界限函数剪去得不到最有解的子树。