【YBT2023寒假Day13 B】马可波罗(博弈论)(数学)

马可波罗

题目链接:YBT2023寒假Day13 B

题目大意

有 n 堆石子,每对有 ai 个,两个人轮流取,每次可以选一堆石子,取至少 1 个至多 x 个石子。
无法操作着输。
然后问你当 x 分别是 1~n 时,是先手必胜还是后手必胜。

思路

首先博弈论经典结论是一对石子的 SG 值是 aimod(x+1),若干堆石子是每一堆的异或和。
那问题就是对于每个 2xn+1aimodx 的异或和是否为 0

那首先取模不太好处理,把它转一下:
aimodx=aixaix
于是考虑我们枚举 x0knx(那这里是 nlogn 的),考虑算 [kx,(k+1)x1] 部分的贡献,也就是这里面的数减去 kx 之后的异或和。

那我们考虑一位一位算贡献,设 fi,ja 里面所有 i 的数减去 i 之后第 j 位的异或和。
那转移我们就每 2j+1 的长度考虑一次(因为这样减去 i 和减去 i+x2j+1 对于第 j 位的 0/1 是没有改变的),设 o(l,r)a 数组中值域在 lr 之间的个数。
那就是:fi,j=o(i+2j,i+2j+11)fi+2j+1,j

然后看如何统计答案,我们设 l=kx,r=(k+1)x1,我们就就找到一个最大的 z 使得 l+2j+1zr,那后缀和一下就是 [l,l+2j+1(z+1)1] 的贡献除去 [r+1,l+2j+1(z+1)1] 的贡献。
[l,l+2j+1(z+1)1] 这个我们可以直接是 fl,jfl+2j+1(z+1),j,至于后面那个,因为这里面的长度不超过 2j+1,所以我们可以类似于一个暴力统计,直接看 o(max(r,l+2j+1z+2j1)+1,l+2j+1(z+1)1) 就可以了。
(答案就是把这三个异或起来,因为减去在异或中就是异或)

代码

#include<cstdio> #include<algorithm> using namespace std; const int N = 2e6 + 100; int n, a[N], b[N], m, g[N], f[N][22]; int o(int l, int r) { if (r < 1) return 0; if (l > n) return 0; if (r > n) r = n; if (l < 1) l = 1; return g[r] ^ g[l - 1]; } int re; char c; int read() { re = 0; c = getchar(); while (c < '0' || c > '9') c = getchar(); while (c >= '0' && c <= '9') { re = (re << 3) + (re << 1) + c - '0'; c = getchar(); } return re; } int main() { freopen("stone.in", "r", stdin); freopen("stone.out", "w", stdout); n = read(); for (int i = 1; i <= n; i++) a[i] = read(), g[a[i]] ^= 1; for (int i = 1; i <= n; i++) g[i] ^= g[i - 1]; for (int i = n; i >= 0; i--) { for (int j = 0, j2 = 1, j12 = 2; j2 <= n + 1; j++, j2 <<= 1, j12 <<= 1) { f[i][j] = o(i + j2, i + j12 - 1) ^ f[i + j12][j]; } } for (int i = 2; i <= n + 1; i++) { int ans; for (int j = 0, j2 = 1, j12 = 2; j2 <= i; j++, j2 <<= 1, j12 <<= 1) { ans = 0; for (int k = 0; k * i <= n; k++) { int l = i * k, r = i * (k + 1) - 1; int z = (r - l) / j12; ans ^= f[l][j] ^ f[l + j12 * (z + 1)][j] ^ (o(max(r, l + j12 * z + j2 - 1) + 1, l + j12 * (z + 1) - 1)); } if (ans) break; } if (ans) printf("Alice "); else printf("Bob "); } return 0; }

__EOF__

本文作者あおいSakura
本文链接https://www.cnblogs.com/Sakura-TJH/p/YBT2023Day13_B.html
关于博主:评论和私信会在第一时间回复。或者直接私信我。
版权声明:本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!
声援博主:如果您觉得文章对您有帮助,可以点击文章右下角推荐一下。您的鼓励是博主的最大动力!
posted @   あおいSakura  阅读(29)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 25岁的心里话
· 按钮权限的设计及实现
历史上的今天:
2022-02-22 【luogu P6242】【模板】线段树 3(吉司机线段树)
2022-02-22 【NOI2021模拟测试赛(四十二)】D(cdq分治)(树状数组)
2022-02-22 【NOI2021模拟测试赛(四十二)】chemistry(珂朵莉树)(动态开点线段树)
2021-02-22 【luogu P3690】【模板】Link Cut Tree (动态树)
2021-02-22 【luogu P3384】【模板】轻重链剖分
2021-02-22 【ybt金牌导航5-1-1】【luogu P2590】树的统计
2021-02-22 【ybt金牌导航4-5-1】【luogu P3369】普通平衡树(替罪羊树做法)
点击右上角即可分享
微信分享提示