Magic Index;及鸡蛋挺住体分析

开发 前端
给定一个数组A,其中有一个位置被称为Magic Index,含义是:如果i是Magic Index,则A[i] = i。假设A中的元素递增有序、且不重复,请给出方法,找到这个Magic Index。更进一步,当A中允许有重复的元素,该怎么办呢?

今日面试题:

给定一个数组A,其中有一个位置被称为Magic Index,含义是:如果i是Magic Index,则A[i] = i。假设A中的元素递增有序、且不重复,请给出方法,找到这个Magic Index。更进一步,当A中允许有重复的元素,该怎么办呢?

鸡蛋挺住体分析:

原题描述

两个软硬程度一样但未知的鸡蛋,它们有可能都在一楼就摔碎,也可能从一百层楼摔下来没事。有座100层的建筑,要你用这两个鸡蛋通过最少的次数确定哪一层是鸡蛋可以安全落下的***位置。可以摔碎两个鸡蛋

方法分析

看到这个题目,最保险的方法就是一层一层试验,但这样只需要一个鸡蛋就可以了。我们现在有两个鸡蛋,完全可以用有更快的方法。

进一步呢?可能试验的方法是二分查找,例如,***个鸡蛋再50层扔下,如果碎了,第二个鸡蛋从1-49逐层试验;如果没碎,***个鸡蛋在75层扔 下,如果碎了,第二个鸡蛋从51-74逐层试验…但是,这个方法,很容易悲剧,例如,当正好49层是可以安全落下的,需要尝试50次。比只有一个鸡蛋的情 况,效果还要差。

上面的分析都是从鸡蛋的角度出发的,想要得到最少的尝试次数,似乎比较难。那如果我们换个角度,从每个高度的楼层来看呢?如果,某个楼层是可以安全落下的,那么最少需要多少次尝试呢?看下面的分析

在我们编程解决问题的过程中,如果遇到***问题的时候,往往可以先尝试一下动态规划的方法。而动态规划的方法,首要的我们要找到构成这个***问题的 ***子问题。所以,下面的分析,我们首先尝试动态规划的方法,如何解决这个问题,这也是典型的程序员的思路;其次,在众多的问题当中,有不少可以直接归结 为数学方程式,如果我们能够写出数学方程式,那么,答案将是更加的简洁、美妙。所以,第二个方法,将尝试如果总结出数学方程式。

基于动态规划的方法

前面提到,若要采用动态规划的方法,最重要的是要找到子问题。做如下的分析,假设f{n}表示从第n层楼扔下鸡蛋,没有摔碎的最少尝试次数。***个鸡蛋,可能的落下位置(1,n),***个鸡蛋从第i层扔下,有两个情况:

  1. 碎了,第二个鸡蛋,需要从***层开始试验,有i-1次机会

  2. 没碎,两个鸡蛋,还有n-i层。这个就是子问题了f{n-i} 所以,当***个鸡蛋,由第i个位置落下的时候,要尝试的次数为1 + max(i - 1, f{n - i}),那么对于每一个i,尝试次数最少的,就是f{n}的值。状态转移方程如下: f{n} = min(1 + max(i - 1, f{n - 1}) ) 其中: i的范围为(1, n), f{1} = 1 完毕。

推广

动态规划的方法,可以推广为n层楼,m个鸡蛋。如下分析: 假设f{n,m}表示n层楼、m个鸡蛋时找到***楼层的最少尝试次数。当***个鸡蛋从第i层扔下,如果碎了,还剩m-1个鸡蛋,为确定下面楼层中的安全楼 层,还需要f{i-1,m-1}次,找到子问题;不碎的话,上面还有n-i层,还需要f[n-i,m]次,又一个子问题。 状态转移方程如下: f{n, m} = min(1 + max(f{n - 1, m - 1}, f{n - i, m}) ) 其中: i为(1, n), f{i, 1} = 1

基于数学方程的方法

假设最少尝试次数为x,那么,***个鸡蛋必须要从第x层扔下,因为:如果碎了,前面还有x - 1层楼可以尝试,如果没碎,后面还有x-1次机会。如果没碎,***个鸡蛋,第二次就可以从x +(x - 1)层进行尝试,为什么是加上x - 1,因为,当此时,***个鸡蛋碎了,第二个鸡蛋还有可以从x+1 到 x + (x - 1) - 1层进行尝试,有x - 2次。如果还没碎,那***个鸡蛋,第三次从 x + (x - 1) + (x - 2)层尝试。碎或者没碎,都有x - 3次尝试机会,依次类推。那么,x次的最少尝试,可以确定的***的楼层是多少呢? x + (x - 1) + (x - 2) + … + 1 = x(x+1) / 2 那反过来问,当***楼层是100层,最少需要多少次呢?x(x+1)/2 >= 100, 得到x>=14,最少要尝试14次。

原文链接:http://www.ituring.com.cn/article/49818

责任编辑:陈四芳 来源: 图灵社区
相关推荐

2013-10-16 16:42:19

矩阵

2023-03-29 07:39:38

TikTok数据安全

2016-12-12 12:37:45

结构C代码赋值

2010-03-01 14:10:23

Magic Linux

2012-03-19 17:36:13

三星

2019-10-21 13:12:41

数据分析增强分析人工智能

2009-08-13 15:41:50

C#结构体指针

2015-02-11 15:23:13

微信SDK

2013-09-18 09:27:57

2010-11-18 11:26:50

IT人

2021-08-09 11:15:28

MybatisJavaSpring

2015-11-12 10:07:52

AWSAWS认证职业资格认证

2021-01-29 19:57:30

NLP 工具TurboNLPExp

2009-11-16 11:03:44

Oracle INDE

2012-08-02 11:11:32

室外一体化UPS

2012-04-06 10:22:58

Magic Reade

2009-06-01 10:06:41

Magic Linux2.5 alpha2

2009-06-23 21:03:55

Linux

2012-02-23 12:53:40

JavaPlay Framew
点赞
收藏

51CTO技术栈公众号