這個問題就是著名的 巴什博奕(Bash Game)
巴什博奕(Bash Game):只有一堆n個物品,兩個人輪流從這堆物品中取物,規定每次至少取一個,最多取m個。最後取光者得勝。分析
一堆物品共 n 個,兩人輪流從中取物,規定每次至少取一個,最多取m 個。最後取光者得勝。
設
n=(m+1)q+r \quad( 0\leq r \leq m ) \\
\quad (\text{i})\quad 若 r=0 ,後取者必勝,策略如下:
若先取者拿走 k 個,則後取者拿走 m+1-k 個,結果剩下 (m+1)(q-1) 個,保持這種取法,則後取者必勝。
\quad (\text{ii})\quad 若 r≠0 ,先取者必勝,策略如下:
先取者先拿走 r 個,若後取者拿走 k 個,則先取者拿走 m+1-k 個,結果剩下 (m+1)(q-1) 個,保持這種取法,則先取者必勝。
總之,要保持給對手留下(m+1) 的倍數,就能最後獲勝。
擴充套件
若規定最後取光者輸,設
n-1=(m+1)q+r \quad( 0≤r≤m ) \\
\quad (\text{i})\quad 若 r=0 ,後取者必勝,策略如下: 若先取者拿走 k 個,則後取者拿走 m+1-k 個,結果剩下 (m+1)(q-1)+1 個,保持這種取法,先取者將取到最後一個物品。
\quad (\text{i})\quad 若 r≠0 ,先取者必勝,策略如下: 先取者先拿走 r 個,若後取者拿走 k 個,則先取者拿走 m+1-k 個,結果剩下 (m+1)(q-1)+1 個,保持這種取法,後取者將取到最後一個物品
小遊戲
兩個人輪流報數,每次至少報一個,最多報十個,誰能報到100 者勝。
附程式碼:
#include
<cstdio>
#include
<string.h>
#include
<queue>
#include
<algorithm>
#include
<iostream>
using
namespace
std
;
int
main
()
{
int
T
;
scanf
(
"%d"
,
&
T
);
while
(
T
--
){
int
n
,
m
;
scanf
(
"%d%d"
,
&
n
,
&
m
);
if
(
n
%
(
m
+
1
))
printf
(
"first
\n
"
);
else
printf
(
"second
\n
"
);
}
return
0
;
}
參閱:
[1]巴仕博弈(Bash Game)小結
[2]Bash Game hdu 1846
[3]巴什博弈_百度百科