【题意】给出总石子数n,和m堆石子,两个人轮着取石子,每次只能从总石子中取m堆中的一堆的个数的石子,取走最后一个石子的胜。S先取,O后取。
【解题思路】这个题我不会,网查大牛做法,好巧妙!!!
【状态表示】dp[i]表示当前剩余石子数为i的时候,1表示s取胜,0表示o取胜!
【状态转移】。转移方程为当 i -a[j]>=0而且dp【i - a[j]】=0(0<=j<m),dp【i】=1;
【总结】实质就是考虑当前s的必胜态由哪个o的必败态转移而来!
【AC代码】
#include <stdio.h>
#include <time.h>
using namespace std;
int a[11];
bool dp[1000001];
int main()
{
int n,m;
while(~scanf("%d",&n))
{
scanf("%d",&m);
for(int i=0; i<m; i++)scanf("%d",&a[i]);
dp[0]=0;
for(int i=1; i<=n; i++)
{
dp[i]=0;
for(int j=0; j<m; j++)
{
if(i>=a[j]&&dp[i-a[j]]==0)
{
dp[i]=1;
break;
}
}
}
if(dp[n])puts("Stan wins");
else
puts("Ollie wins");
}
return 0;
}