一个有趣的面试题:伞兵跳伞问题

这道题是今天同事分享给我们做的,题目挺难的,也挺有意思的,一堆清北的人围在一起讨论了半个多小时,最后还是一个搞过ACM的人想出来了解法。特此把这道题和解法都分享一下。

题目描述

有n个伞兵从飞机上跳伞,伞兵落地后会昏迷一段时间,等到醒来后能看一眼雷达,雷达上能显示包括自己在内所有人的位置,但是雷达上显示的只是相对位置,没有东南西北这种方向,伞兵看完这一次雷达后就再也不能看了。
要求:设计一个策略能让伞兵落地后经过一系列运动最终所有人都走到一起去

补充说明

  1. 可以认为所有伞兵都同时落地,但是每个伞兵昏迷的时间长度不同
  2. 可以认为伞兵的记忆力都非常好,看完雷达之后能够一直记住,而且伞兵走路能够精确的走多少步还有方位。
  3. 不能给伞兵编号,因为每个伞兵都是相同的。(因为如果能编号,则可以直接1号伞兵去寻找其他所有人,剩余的伞兵不动就好)
  4. 伞兵会面之后可以有交流的
  5. 最后这个策略是所有伞兵在跳伞前都知道的。

思路历程

因为每个伞兵都是相同的个体,不能编号,所以一个非常直观的思路就是,需要伞兵醒来之后,看到的雷达上的图形,去在图中寻找一个其他伞兵也能找的点
所以一开始想法是找所有伞兵的中点,但是考虑到每个伞兵醒来的时间不一致,这就导致了先前醒来的伞兵在行动之后,中点会发生变化。所以士兵要去的这个点还必须随着士兵的移动不发生改变。
但是到这里就陷入了僵局,我们无论如何也找不到一个点,不随着士兵的移动而不发生变化。
这时也离最终答案就差一步了,就是需要想到可以让有些士兵不动,另外一些士兵去找那些不动的士兵所构成图形的点就好

答案

  1. 所有伞兵都落地后,可以找到一个最小外接圆将所有伞兵都围在圆内,这个圆是唯一的。
  2. 然后所有圆上的伞兵都不动,圆内的伞兵都往圆中心走。
  3. 因为伞兵醒来时间不同所以大家到达圆心的时间是不同,但是当最后一个伞兵到达圆心的时候(因为伞兵可以观察到现在圆心中有几个伞兵,算一下就知道是不是最后一个到达了)
  4. 然后中心圆点的伞兵出发到圆周上,绕圆一周把圆周上的伞兵集齐

后来想到,其实不一定非要用圆,找到闭包就好,闭包构成的多边形上的点不动,然后其余的人去到这个多边形的重心,而后再沿闭包多边形的边找就好。

补充

当面的解法有个小疏漏就是当n=3时,该如何做;或者当所有伞兵的点都在圆环上时该如何做。
我的解法是这样的:
还是做一个外接圆,然后找到外接圆上沿着圆周距离最短的两个点,让这两个点沿着圆周相互靠近,等到相遇的时候,再沿着圆周把其余所有点都找齐。
为什么这样可行,因为如果两个点距离最短那么他们在靠近的时候依旧能够保持着这个性质,所以之后苏醒的人也不会改变这个观测结果。
不过这里还会遇到一个问题,如果一个点两边两个点都距离相等且最小怎么办,那就随机往一个点走就好,因为两边两个点必然也往你这边走,总会碰到其中一个,而另外一个则走到中间那个点那停住就好。
最后还有种最极端的情况,所有点距离都相等,即等距的分布在圆周上,且伞兵同时醒来,且伞兵都按照。
对于这种情况,再加一个补丁:

  1. 当伞兵醒来发现是个等边,那就需要更新策略,比如每个伞兵都走到下一个人的位置之后,不停下继续走等走满一个圆周(这样做是为了防止有些人还在昏迷)
  2. 如果走满圆周后,还是没有碰到人,那么就往一开始的圆心走
  3. 如果走在圆周上碰到了人,就带着那个人一起走,走满之后再往圆心走

你可能感兴趣的:(面试)