【BZOJ】3895: 取石子
【算法】博弈论+记忆化搜索
【题意】给定n堆石子,两人轮流操作,每个人可以合并两堆石子或拿走一个石子,不能操作者输,问是否先手必胜
【题解】
首先,若所有石子堆的石子数>1,显然总操作数为(石子数+石子堆数-1),奇数先手必胜,偶数先手必败。
若有部分石子堆的石子数=1,情况较复杂,考虑一下五种情形:
1. 拿走石子数=1的石子堆
2.减少操作次数(拿走石子或合并石子堆)
3.操作数减至1时,视为多一堆石子数=1的石子堆(若操作数不为1,即使出现也会被再次操作抵消)
4.合并两个石子数=1的石子堆
5.合并一个石子数=1和一个石子数>1的石子堆
对于(石子数=1的石子堆数(<=50),总操作数(<=50049))二元组进行记忆化搜索。(记忆化是针对所有数据的统一记忆化,这样50*50049就不会超时)
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std; int n,a[],f[][];
int dfs(int x,int y)
{
if(~f[x][y])return f[x][y];
if(x==)return y&;
if(y==)return dfs(x+,);//
if(x&&!dfs(x-,y))return f[x][y]=;
if(y&&!dfs(x,y-))return f[x][y]=;
if(x>&&!dfs(x-,y++(y?:)))return f[x][y]=;
if(x&&y&&!dfs(x-,y+))return f[x][y]=;
return f[x][y]=;
}
int main()
{
int T;
scanf("%d",&T);
memset(f,-,sizeof(f));
while(T--)
{
scanf("%d",&n);
//memset(f,-1,sizeof(f));
int tmp=,sum=;
for(int i=;i<=n;i++){scanf("%d",&a[i]);if(a[i]==)tmp++;else sum+=a[i];}
if(dfs(tmp,n-tmp-+sum))printf("YES\n");else printf("NO\n");
}
return ;
}
【BZOJ】3895: 取石子的更多相关文章
- bzoj 3895: 取石子
$ \color{#0066ff}{ 题目描述 }$ Alice和Bob两个好朋含友又开始玩取石子了.游戏开始时,有N堆石子 排成一排,然后他们轮流操作(Alice先手),每次操作时从下面的规则中任选 ...
- BZOJ 3895: 取石子[SG函数 搜索]
有N堆石子 ·从某堆石子中取走一个 ·合并任意两堆石子 不能操作的人输. 100%的数据满足T<=100, N<=50. ai<=1000 容易发现基础操作数$d=\sum a ...
- bzoj 3895 取石子——博弈论
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=3895 看题解:https://blog.csdn.net/popoqqq/article/d ...
- bzoj 3895 取石子 —— 博弈论
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=3895 看了博客:https://blog.csdn.net/popoqqq/article/ ...
- bzoj 1874 取石子游戏 题解 & SG函数初探
[原题] 1874: [BeiJing2009 WinterCamp]取石子游戏 Time Limit: 5 Sec Memory Limit: 162 MB Submit: 334 Solved ...
- BZOJ 1874 取石子游戏 - SG函数
Description $N$堆石子, $M$种取石子的方式, 最后取石子的人赢, 问先手是否必胜 $A_i <= 1000$,$ B_i <= 10$ Solution 由于数据很小, ...
- BZOJ 3895 3895: 取石子 / Luogu SP9934 ALICE - Alice and Bob (博弈 记忆化搜索)
转自PoPoQQQ大佬博客 题目大意:给定n堆石子,两人轮流操作,每个人可以合并两堆石子或拿走一个石子,不能操作者输,问是否先手必胜 直接想很难搞,我们不妨来考虑一个特殊情况 假设每堆石子的数量都&g ...
- BZOJ 1413 取石子游戏(DP)
题目链接:http://61.187.179.132/JudgeOnline/problem.php?id=1413 题意:n堆石子排成一排.每次只能在两侧的两堆中选择一堆拿.至少拿一个.谁不能操作谁 ...
- BZOJ 1874 取石子游戏 (NIM游戏)
题解:简单的NIM游戏,直接计算SG函数,至于找先手策略则按字典序异或掉,去除石子后再异或判断,若可行则直接输出. #include <cstdio> const int N=1005; ...
随机推荐
- Coursera:Internet History ,Techornology and Security
WEEK1 War Time Computing and Communication Bletchley Park 布莱彻利庄园:a top-secret code breaking effort b ...
- C++读取文件统计单词个数及频率
1.Github链接 GitHub链接地址https://github.com/Zzwenm/PersonProject-C2 2.PSP表格 PSP2.1 Personal Software Pro ...
- 【IdentityServer4文档】- 贡献
贡献 我们非常乐于接受社区贡献,但您应遵循一些指导原则,以便我们可以很方便的解决这个问题. 如何贡献? 最简单的方法是打开一个问题并开始讨论.然后,我们可以决定如何实现一个特性或一个变更.如果您即将提 ...
- 一个demo让你彻底理解Android中触摸事件的分发
注:本文涉及的demo的地址:https://github.com/absfree/TouchDispatch 1. 触摸动作及事件序列 (1)触摸事件的动作 触摸动作一共有三种:ACTION_DOW ...
- (转)centos6.5下Zabbix系列之Zabbix安装搭建及汉化
最近在研究zabbix,在整理完成之后就有了写一下总结博客的想法,在我研究zabbix的时候给我很大帮助的是it你好,博客地址 http://itnihao.blog.51cto.com/他做的zab ...
- wpf 验证方法
效果图,当放鼠标到文本框上会显示出错的提示.
- CentOS 文件及目录等
1.在linux中一切皆是文件,只是类型不同,通过ls -l看到的一个字母表示文件的类型 -:普通文件. d:目录文件. l:链接文件. b:块设备文件. c:字符设备文件. p:管道文件. 2.文件 ...
- 【原创】Oracle Not In 导致有存在Null的数据被过滤
解决方法: WHERE NVL(ID,) NOT IN ('') 注:红字部分不相等就可以
- 【BZOJ4031】小Z的房间(矩阵树定理)
[BZOJ4031]小Z的房间(矩阵树定理) 题面 BZOJ 洛谷 Description 你突然有了一个大房子,房子里面有一些房间.事实上,你的房子可以看做是一个包含n*m个格子的格状矩形,每个格子 ...
- BZOJ2286:[SDOI2011]消耗战——题解
+++++++++++++++++++++++++++++++++++++++++++ +本文作者:luyouqi233. + +欢迎访问我的博客:http://www.cnblogs.com/luy ...