leetcode(2), Nin Game详解(python)

question:

桌上有堆石头,有很多个,你和对手轮流拿石头。规则是,每次拿的石头数不能超过三个,也不能不拿,谁先拿完石头谁就获胜。例如:有4个石头,你无论先拿几个,1个2个3个,都会有剩下的让对手一次拿完,这样对方就赢了。

现在假设你和对手都很会玩这个游戏,精于计算,需要你根据石头总数,来判断你会不会获胜。


解答:

首先,一定要注意红色的字,你和对手都精于计算!说明你们都很会玩,都有策略的。

看到这个题目,一开始的想法是用两层循环,用枚举法。但是我们可以这样看:

1颗         win拿1

2颗         win拿2

3颗 win 拿3

4颗 lose

5颗 win 拿1,剩4个,对方无论怎么拿都是输

6颗 win 拿2,剩4个,对方无论怎么拿都是输

7颗 win 拿3,剩4个,对方无论怎么拿都是输

8颗 lose


到这里应该可以看出规律,当石头总数<=8 and !=4,只要你拿石头,剩下的石头是4颗,都是你赢。那为什么4颗,8颗的时候你一定输呢?

因为你先拿,对手只用拿让剩下的石头数为4颗的石头数就可以确保赢了。可以推算一下。

由此可以递推,当石头数>8时,且不为4的倍数时,你一定会赢,策略是,拿出石头,使剩下的石头为4的倍数,这样对手一定输,当石头数为4的倍数时,一定会输,对手的策略是,拿出石头,使剩下的石头为4的倍数。

所以这个算法的代码就简单了:

def Nim(n):
	#n为石头数
	if n % 4 == 0:
		print "lose"
	else:
		print "win"


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值