找工作已经跑了一个多月,大大小小的笔试不记得参加了多少场,遇到最多的就是以下两种题目:数据结构和C++深入(尤其是虚函数)、智力题目。网易游戏的题目涉及到许多数学知识,搜狐游戏还好点,可惜死在最后一道题上了,关于贪心算法的一个应用(100分的题目这道题占了43分,晕死)。
前几天福建IT企业组团来电子科大招聘,我看中了榕基软件,因为他们要招几个做网安产品研发的,我的简历应该让他们感到比较满意,问了很多问题,可惜第二天笔试的时候完全考砸了,一共就四道题目,第一题就是我们今天将要介绍的题目,详细介绍:有一根27厘米的细木杆,在第3厘米、7厘米、11厘米、17厘米、23厘米这五个位置上各有一只蚂蚁。木杆很细,不能同时通过一只蚂蚁。开始时,蚂蚁的头朝左还是朝右是任意的,它们只会朝前走或调头,但不会后退。当任意两只蚂蚁碰头时,两只蚂蚁会同时调头朝反方向走。假设蚂蚁们每秒钟可以走一厘米的距离。求所有蚂蚁都离开木杆的最小时间和最大时间。
我苦思冥想了很久也没法算出最大时间,后面三道题做的也不是很顺利,只好无奈接受被淘汰的现实。回来后尝试搜索了一下,果然这道题已经出现过,而且百度的面试题目。
以下答案是从网上搜索而来:
问题分析:
1.最小时间肯定是各自朝最近的一端跑,27-11=14,11<14,所以中间的蚂蚁会朝11cm那端跑,最小时短时间11。
2. 最长时间呢,肯定两端的蚂蚁都往中间跑,具体怎么跑好像有点儿想不清楚,那试算之,假设3cm处的和7cm处的相对而行,碰面后会怎样?如果你眼神不好,你会发现你分不出来哪个是哪个,因为3cm的转头后就相当于7cm的一直在走。到这里,一切就已经没有刚开始那样想不清楚了,事情很清楚:蚂蚁碰头可以用等量代换的思想,在这种情况下,任何蚂蚁都是自由地向它面向的一端直接爬过去。那最长时间就清楚了:27-3=24,27-23=4 24>23,所以最长时间是24。
有了以上分析,算法就简单了。
算法:
1.找出中间的蚂蚁离两端的距离中较小的。
a[2]=11
a[2]'=27-11=14,
因为a[2]<a[2]',所以最小距离是11,时间11/1=11
2.找出两端的蚂蚁距两端的距离中较大的。
a[0]=3
a[0]'=27-3=24
a[4]=23
a[4]'=27-23=4
这四个数中最大的是24。
3.所以,最大时间24,最小时间11
程序:略。
另外的分析,与上述介绍基本相同,但更加透彻易懂:关于这道题目,网上给出了很多的解释,但从整体来看,基本都是用到了等价置换(等量代换)的思想。要求最小时间,即为“最不容易”先到达两端的蚂蚁以最短的时间到达,所以我们只需找到所有蚂蚁中间的一只(共奇数只蚂蚁)或两只(共偶数只蚂蚁)到达一端的最短时间。比较麻烦的是求最长时间,有人会觉得当有很多只蚂蚁时,中间的蚂蚁们相互碰撞的次数多些会增加时间,感觉上比较复杂,可如果我们用等量代换的思想来解释就比较容易。假设中间的任意两只相邻蚂蚁即将发生碰撞,如:A -> <-B,当A,B发生碰撞后,便有<-A B->。A,B反向相当于<-B A -> ,即二者继续向着原来的方向前进,对于任意相邻的发生碰撞的蚂蚁都适用,所以只需求最两端的两只蚂蚁距离两端的最远距离。由以上分析可知,如果出这样的问题,我们可以不用通过程序便能说出结果:5个点,中间蚂蚁的位置为11,即0-11-27,显然最小为11,最两端蚂蚁,0-3-27,最大为 24,0-23-27,最大为23,所以最大为24。
附Java解题程序(C语言写的话比较麻烦,C++懒得写):
public class Ant {
//蚂蚁的位置
private int position;
//爬行方向
private boolean front_flg;
//是否到达终点
private boolean isOver = false;
//蚂蚁的名字
private String antName;
public boolean isOver() {
if((position == 0)||(position == 27)){
isOver = true;
} else {
isOver = false;
}
return isOver;
}
public void setOver(boolean isOver) {
this.isOver = isOver;
}
public String getAntName() {
return antName;
}
public void setAntName(String antName) {
this.antName = antName;
}
public boolean isFront_flg() {
return front_flg;
}
public void setFront_flg(boolean front_flg) {
this.front_flg = front_flg;
}
public void setPosition(int position) {
this.position = position;
}
//构造方法
public Ant (int position,boolean flg,String antName){
this.position = position;
this.front_flg = flg;
this.antName = antName;
}
public void crawl(boolean front_flg){
//根据爬行方向判断position的加减
if(!(isOver())){
if (front_flg){
position = position + 1;
} else {
position = position - 1;
}
}
System.out.println(antName + " has arrived position : " + position);
}
public int getPosition() {
return position;
}
/**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
Ant ant3 = new Ant (3,true,"ant3");
Ant ant7 = new Ant (7,true,"ant7");
Ant ant11 = new Ant (11,true,"ant11");
Ant ant17 = new Ant (17,false,"ant17");
Ant ant23 = new Ant (23,false,"ant23");
//记录爬行时间
int useTime = 1;
while(!(ant3.isOver()
&&ant7.isOver()
&&ant11.isOver()
&&ant17.isOver()
&&ant23.isOver())){
//如果两只蚂蚁相遇则调转爬行方向
if (ant3.getPosition()==ant7.getPosition()){
boolean temp;
temp = ant3.isFront_flg();
ant3.setFront_flg(ant7.isFront_flg());
ant7.setFront_flg(temp);
}
if (ant3.getPosition()==ant11.getPosition()){
boolean temp;
temp = ant3.isFront_flg();
ant3.setFront_flg(ant11.isFront_flg());
ant11.setFront_flg(temp);
}
if (ant3.getPosition()==ant17.getPosition()){
boolean temp;
temp = ant3.isFront_flg();
ant3.setFront_flg(ant17.isFront_flg());
ant17.setFront_flg(temp);
}
if (ant3.getPosition()==ant23.getPosition()){
boolean temp;
temp = ant3.isFront_flg();
ant3.setFront_flg(ant23.isFront_flg());
ant23.setFront_flg(temp);
}
if (ant7.getPosition()==ant11.getPosition()){
boolean temp;
temp = ant7.isFront_flg();
ant7.setFront_flg(ant11.isFront_flg());
ant11.setFront_flg(temp);
}
if (ant7.getPosition()==ant17.getPosition()){
boolean temp;
temp = ant7.isFront_flg();
ant7.setFront_flg(ant17.isFront_flg());
ant17.setFront_flg(temp);
}
if (ant7.getPosition()==ant23.getPosition()){
boolean temp;
temp = ant7.isFront_flg();
ant7.setFront_flg(ant23.isFront_flg());
ant23.setFront_flg(temp);
}
if (ant11.getPosition()==ant17.getPosition()){
boolean temp;
temp = ant11.isFront_flg();
ant11.setFront_flg(ant17.isFront_flg());
ant17.setFront_flg(temp);
}
if (ant11.getPosition()==ant23.getPosition()){
boolean temp;
temp = ant11.isFront_flg();
ant11.setFront_flg(ant23.isFront_flg());
ant23.setFront_flg(temp);
}
if (ant17.getPosition()==ant23.getPosition()){
boolean temp;
temp = ant17.isFront_flg();
ant17.setFront_flg(ant23.isFront_flg());
ant23.setFront_flg(temp);
}
//蚂蚁爬行
ant3.crawl(ant3.isFront_flg());
ant7.crawl(ant7.isFront_flg());
ant11.crawl(ant11.isFront_flg());
ant17.crawl(ant17.isFront_flg());
ant23.crawl(ant23.isFront_flg());
System.out.println("Use time is :" + useTime++);
System.out.println("================================");
}
}
}
唉,从别人的解法中看到了自己的差距啊!!!