可怜的小猪--进制数的妙用

可怜的小猪--进制数的妙用

题目

有1000个桶,有且仅有一个桶里面装了毒药,其他的都装了水。这些桶从外面看上去完全相同。如果一只猪喝了毒药,它将在15分钟内死去。在一个小时内,至少需要多少只猪才能判断出哪一个桶里装的是毒药呢?

代码

	/***
	 * @param buckets  桶的数量
	 * @param minutesToDie  毒药发作时间
	 * @param minutesToTest  最短测试时间
	 * @return
	 */
	public static int getPigs(int buckets ,int minutesToDie ,int minutesToTest){
		//如果只有一桶水,那么就可以直接确定了
		if(buckets <2){
			return 0;
		}
		int dimension = minutesToTest / minutesToDie  + 1;  //维度
		int pig = 0;
		int res = 1; 
		//buckets至少是2,因此一定进入循环,因此pig一定不会是0
		while(res<buckets){
			res = res * dimension;  //每增加一头猪,则以维度的倍数增加可以测试的水桶
			pig++;
		}
		return pig; 
	}

解题逻辑

思路:
以下思路是看过解析的…

首先根据题目的要求是我们至少需要多少只猪,那么我们假定一只猪的情况下,可以测试多少水桶呢?
一只猪在一个小时内最多可以测试四次,每隔15分钟测一次。那么就有五种状态:15分钟后死,30分钟后死亡,45分钟后死亡,60分钟后死亡,还有一种就是没有死亡。那么一只猪的情况下就可以测试五桶水(在假定只有五桶水的情况下,最后一桶是可以不用测的,既然前面四桶都是安全的,那么最后一桶肯定是有毒的)。
一只猪的情况下已经知道了,如果还没看出规律,那就看看两只猪的情况:这个时候需要借助一些东西了,比如二维数组,二维矩阵,平面直角坐标系等二维的东西来表示。下面看一个图

00 01 02 03 04
10 11 12 13 14
20 21 22 23 24
30 31 32 33 34
40 41 42 43 44

一个二维矩阵,下面就看一下怎么理解:
第一次 第一只猪喝第一行的,第二只猪喝第一列的,那么如果毒药在第一个(00),那么两只猪15分钟后都死亡。如果第一只猪死亡,那么毒药就在第一行。第二只猪的情况同理。
第二次 第一只猪喝第二行,第二只猪喝第二列(这里是毒药不在第一行和第二列的情况下),情况分析参考第一次喝水;假设第一支猪已经死亡,那么第二只猪这次也死亡,那么就在第一行第二列。就这么分析
第三次…
第四次 如果两只猪都没有死亡,那么就是最后一个有毒了(44)

最后说明一下:第一次喝水是在0分钟,第二次喝水是15分钟,第三次喝水时30分钟,第四次喝水是45分钟。

规律大概出来了,一只猪可以测5桶水,两只猪可以测25桶水,随着猪的数量的递增,就将可测试数量乘以五;规律就是五的次幂的运用,或者说可以把每一只猪看成是一位五进制数。那么为什么是五进制或者说是五的倍数呢,这个就对应猪的状态了,猪可以有的状态刚好就是五种,假设猪的状态只有两种,那么就是2的倍数了。

ok,那么看看三只猪的情况 两只猪是二维,那么三只猪就是三维,可以理解为000 0001 … 那么当成五进制来看,那就是可以测125(5 * 5 * 5)次了,要是想具体一点,可以参考空间直角坐标系,就是一个长为1的正方体。

有点啰嗦,并且没有动图…

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值