首先说说上下文:

博客园内两篇关于此题的讨论

http://www.cnblogs.com/beginor/archive/2009/04/27/1444844.html
http://www.cnblogs.com/ilovemeyou2000/archive/2009/04/29/1445797.html

这道"有趣"的面试题是:甲乙两地相距100公里,有一辆火车以每小时15公里的速度离开甲地直奔乙地,另一辆火车以每小时20公里的速度从乙地开往甲地。如果有一只鸟,以30公里每小时的速度和两辆火车同时启动,从甲地出发,碰到另一辆车后返回,依次在两辆火车来回飞行,直到两辆火车相遇,请问,这只小鸟往返了多少次

首先说这个题,我觉得出的并无任何不严谨的地方,也没有能明显让人误解的地方。按照通常的表述,显然题意是忽略鸟的转身时间,忽略鸟的身长,把鸟和火车头抽象成三个点。如果非要考虑鸟的转身时间和身长,我觉得有故意曲解的嫌疑。任何一个应用问题都有隐含的忽略条件,答题者如果要求应用题表述无限精确滴水不漏,是不可能的。所以我觉得有些关于量子物理的言论就没有必要了。如果硬要钻牛角尖,还可以说火车道不是严格的直线,可以说鸟并非匀速直线运动,可以说根据相对论速度和距离、时间应该遵守洛伦兹变换而非伽利略变换。

然后是解法,按照原意,鸟往返了无限多次,可以用数学归纳法证明:

假设第k次两车相距m 小鸟在甲车处
飞到乙车时 两车相距
m-m/(20+30)*(15+20)=0.3m
再飞到甲车
0.3m-0.3m/(15+30)*(15+20)=1/15m

第k+1次往返两车距离为m/15

显然若m>0 第k+1次之后两车距离仍不为0

开始是两车相距100公里不为0  所以不论往返多少次 两车距离都不为0 

本来解到这里,这个题目应该已经可以得出答案了。

但是很多朋友为了编程可实现,规定了一个距离精度,小于这个距离就认为两车相距,然后又递归或者迭代写了代码实现。但是程序员不是编码工,不是所有能实现的代码就是好的。不能只知道模拟,不考虑效率。

根据前面的证明 其实最后往返次数只是一个对数运算(注意求的是往返次数,而不是转身次数)


using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace bird
{
    
class Program
    {
        
static void Main(string[] args)
        {
            
double exactDistance = 0.000000001;
            Console.WriteLine(Convert.ToInt32(Math.Ceiling(System.Math.Log(exactDistance 
/ 10001.0 / 15))));
        }
    }
}

最后关于时间无限细分的问题 其实类似很多年前就被提出并解决了:http://en.wikipedia.org/wiki/Zeno's_paradoxes

而且类似的计时制中,次数并不是一个悖论,距离才是。

所以这个问题作为面试题,是非常不错的题目,可以从不同的角度回答者的能力:

1.数学和逻辑思维基础:考察面试者是否了解类似的问题并且知道背景知识,能否独立想出解决方案

2.算法优化意识:考察面试者是否仅仅关注最表面的解决方法。二话不说直接写递归交差的程序员肯定不要

3.理解问题能力:考察面试者是否能正确理解问题,理解有偏差时,是否能主动沟通,弄清别人的真正意图。自己假设一堆条件的程序员肯定不要

4.编程语言基础:考察面试者是否能正确运用一门计算机语言。用==直接比较浮点数的程序员肯定不要

[Reprinted from http://www.cnblogs.com/winter-cn/archive/2009/04/30/1446636.html]

----------------------------------------------------------------------------------------------------------------------------------

给出一个IT同行“愚公”,详细且比较合理的解释,呵呵。

首先,明确一下【往返次数】的定义:
从开始时鸟从甲车出发开始,以后每次遇见一次甲车算一个往返。

设甲车速度为v1,乙车速度为v2,鸟速度为v3,两车初始距离为S,鸟和甲同一初始点.两车相遇的时刻为T,求鸟出发后再与甲车相遇的次数X.
那么,
情况一: v3<v1, 直到两车相遇,鸟不会出现在两车之间,X=0
情况二: v3==v1, 鸟与甲车同速前进,遇到乙车,没有往返,X=0
情况三: v3>v1 && v3==v2,鸟将与乙车同时遇见甲车,X=1
情况三: v3>v1 && v3<v2,直到两车相遇,鸟不会遇见甲车,X=0
情况三: v3>v1 && v3>v2,这是最复杂的情况,简单的逻辑可以得知,当两车距离越近时,鸟在两车之间往返的频率越高,两车距离趋近0时,单位时间鸟的往返次数趋近+∞,X→+∞

这个需要算么?基本上不用算,但不是不可以算。

情况三如果要计算,只能给出一个以大于0的两车距离为参数的函数,或以小于T的时间点为参数的函数。
记鸟第k次遇见甲时,甲乙相距S[k];
鸟第k+1次遇见甲时,甲乙相距S[k+1];

计算得出下公式:

S[k+1]    (v1-v3)(v2-v3)
───── = ─────────
S[k]     (v1+v3)(v2+v3)

也就是说,S[k]是一个等比数列。
问题就简单明确了
剩下的我就不多说了

posted on 2009-05-01 01:28  GT_Andy  阅读(580)  评论(0编辑  收藏  举报