您的位置:首页 > 其它

【BZOJ】【1874】取石子游戏

2015-01-03 20:44 148 查看

SG函数

  嗯博弈论入门题,关于SG函数这个东西可以去看VFK神犇的博客,讲的非常清楚Orz。

  传送门:vfleaking.blog.163.com/blog/static/174807634201231792341827/

     http://vfleaking.blog.163.com/blog/static/174807634201391304748444/
  

  然后这题直接暴力求SG函数就好了……反正数据规模也不大。

  

//BZOJ 1874
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<iostream>
#include<algorithm>
#define rep(i,n) for(int i=0;i<n;++i)
#define F(i,j,n) for(int i=j;i<=n;++i)
#define D(i,j,n) for(int i=j;i>=n;--i)
using namespace std;
const int N=1010;
#define debug
int n,m,a[11],b[11],SG
;
bool mark
;
void calsg(){
F(i,1,1000){
memset(mark,0,sizeof mark);
F(j,1,m) if (i-b[j]>=0)
mark[SG[i-b[j]]]=1;//利用SG函数原本的定义
//i的后继状态即为 i-b[j]
//SG[i-b[j]]为后继状态到不了的状态
//所以那个状态i也到不了
F(j,0,10) if (!mark[j]) {SG[i]=j; break;}
}
}

int main(){
#ifndef ONLINE_JUDGE
freopen("file.in","r",stdin);
#endif
scanf("%d",&n);
F(i,1,n) scanf("%d",&a[i]);
scanf("%d",&m);
F(i,1,m) scanf("%d",&b[i]);
calsg();

int temp=0;
F(i,1,n) temp^=SG[a[i]];

if (temp){
printf("YES\n");
F(i,1,n)
F(j,1,m)
if(SG[a[i]-b[j]]==(temp^SG[a[i]])){
printf("%d %d\n",i,b[j]);
return 0;
}
}
else printf("NO\n");
return 0;
}


View Code
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: