ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

CF1033G Chip Game 博弈

2022-03-31 08:31:05  阅读:197  来源: 互联网

标签:le max sum Game ge win 情况 Chip CF1033G


看的跳蛙题解,只是瞎嘴巴一遍加深印象。

模拟赛出题人搬来的CF *3500=.=

于是我的一整个晚上就被吃了。

题意

现在有一种隔膜。有 \(n\) 堆棋子,MC 和 pigstd 轮流取,MC每次只能取 \(a\) 个,pigstd 每次只能取 \(b\) 个。

问,对于所有满足 \(a,b\in [1,m]\) 且 \(a,b\in Z\) 的 \((a,b)\) ,假设MC和pigstd都绝对聪明,分别有几种方案满足如下四种情况。

  • MC win
  • pigstd win
  • 先手 win
  • 后手 win

\(n\le 10^2, m\le 10^5\) ,每堆棋子数量 \(\le 10^{18}\)

题解

因为只有pigstd 真的是人win,所以答案是 \(0,m^2,0,0\) 。做完了。

对于 \((a,b)\)

  • MC win: 拿 \(a\) 的必胜
  • pigstd win: 拿 \(b\) 的必胜
  • 先手 win:谁先手谁胜
  • 后手 win:谁后手谁胜

显然四种情况是不会有重叠的,容易发现 MC win 和 pigstd win 的情况是等价的。

那么其实只要考虑先手必胜和后手必胜的方案数,然后就能求出所有答案。


\(G=(v_0,v_1,...)\) 的局面等价于 \(G‘=(v_0\bmod (a+b), v_1\bmod (a+b),...)\) 的局面。好像可以解释成,分成了两个子游戏,因为这两个游戏的赢家先后手不变,所以其中有一个是 \(0\) ,那么总的异或和不为0。
那么我们的 \(v_i\) 就会减小到 \(2m\) 以内了。


叫起来太麻烦了。。还是 A 每次拿 \(a\) ,B 每次 拿 \(b\) 好了。

我们现在只考虑先手胜还是后手胜的问题,所以我们不妨设 A 是 小手,B 是大手(也就是 \(a\le b\))

  • 情况1:\(v_i\in [0,a)\) 废点。不用管。
  • 情况2:\(v_i\in [a,b)\) A 可拿 1 次,B拿不了。
  • 情况3:\(v_i\in [b,2a)\) A 可拿 1 次,B拿 1 次。
  • 情况4:\(v_i\in [max(2a,b),a+b)\) A 可拿 2 次,B 拿 1 次。

我们注意到每堆最多被一个人拿。

分类讨论。被括起来的是必胜者。

  • (A)存在情况2。
  • 不存在情况2
    • (A)情况 4 个数 \(\ge 2\):那么,第一轮里, A 肯定可以和 B 抢到一个情况4,将它转化为情况2。
    • 情况 4 个数 \(=1\)。
      • 情况3 和情况 4 个数(\(\sum [v_i\ge b]\)) 为奇数。
        • (A)A是先手
        • (B)B是先手
      • (A)情况3 和情况 4 个数(\(\sum [v_i\ge b]\)) 为偶数。
    • 不存在情况 4。
      • 情况 3 个数(\(\sum [v_i\ge b]\))是奇数
        • (A)A是先手
        • (B)B是先手
      • 情况 3 个数(\(\sum [v_i\ge b]\))是偶数
        • (B)A是先手
        • (A)B是先手

整合一下。只要考虑先手必胜和后手必胜的 \((a,b)\)。

  • 不存在情况2
    • 情况 4 个数 \(=1\)。
      • (先)\(\sum [v_i\ge b]\) 为奇数
    • 不存在情况 4。
      • (先):情况 3 个数(\(\sum [v_i\ge b]\))是奇数
      • (后):情况 3 个数(\(\sum [v_i\ge b]\))是偶数

那么我们就可以暴力枚举 \(O(nm^2)\) 了。然而过不去。。


考虑先手胜利的情况:

  • 不存在 \(v_i\in [a,b)\)
  • \(\sum [v_i\in [max(2a,b),a+b)]\le 1\) 并且 \(\sum [v_i\ge b]\) 为奇数。

考虑后手胜利的情况:

  • 不存在 \(v_i\in [a,b)\)
  • \(\sum [v_i\in [max(2a,b),a+b)]=0\) 并且 \(\sum [v_i\ge b]\) 为偶数。

首先枚举 \(a+b\)

对 \(v\) 进行排序。

要求 \(a,b\) 就处于一个 \((v_j,v_{j+1}]\) 的区间内。枚举是哪个区间。(边界区间也要考虑)

然后 \(\sum [v_i\ge b]\) 的奇偶性就可知了。分别考虑先手胜和后手胜的情况。

设最大的 \(v\) 是 \(v_n\),次大的是 \(v_{n-1}\)

  • 先手

    \(\sum [v_i\in [max(2a,b),a+b)]\le 1\)

    即:\(max(2a,b)>v_{n-1}\)

    即:必须满足 \(a>\lfloor \frac {v_{n-1}} 2\rfloor\) 和 \(b>v_{n-1}\) 中至少一个

    看起来这个玩意儿需要容斥。但是实际上不用。
    因为 \(a,b\) 在一个区间里,所以 \(b>v_{n-1}\) 的时候 \(a\) 一定 \(>v_{n-1}>\lfloor \frac {v_{n-1}} 2\rfloor\)。所以只需要计算 \(a>\lfloor \frac {v_{n-1}} 2\rfloor\) 的情况。

  • 后手

    \(\sum [v_i\in [max(2a,b),a+b)]=0\)

    即:\(max(2a,b)>v_n\)

    即:\(a>\lfloor \frac {v_n} 2\rfloor\) 或 \(b>v_n\)

    同理。
    因为 \(a,b\) 在一个区间里,所以 \(b>v_{n}\) 的时候 \(a\) 一定 \(>v_{n}>\lfloor \frac {v_{n}} 2\rfloor\)。所以只需要计算 \(a>\lfloor \frac {v_{n}} 2\rfloor\) 的情况。

那么我们最后会框出一个 \(a\) 的范围 \([l,r]\),然后 \(b\in (v_{j},v_{j+1}\bmod s)\)

l = max(v[j] % s, mx / 2) + 1, r = min(v[j + 1] % s, m);

注意到我们开始有个设定叫 \(a\le b\),现在我们想抛弃它,否则会很难写。

那么就是 \(min(a,b)\in [l,r],max(a,b)\in \in (v_{j},v_{j+1}\bmod s)\)

也就是 \(min(a,b)\ge l,max(a,b)\le r\)

\(a\ge l,b\ge l,a\le r,b\le r\)

那么最终 \(a\) 的范围就是 \([min(l,s-r),max(r,s-l)]\)

太困难啦!谢谢 @shight 答了一堆奇奇怪怪的疑。

代码

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
#define ls(x) ((x)<<1)
#define rs(x) ((x)<<1|1)
#define fi first
#define se second
#define mkp make_pair
#define PII pair<int,int>
const int N = 110, M = 2e5 + 10;
int n, m, tmp[N];
ll v[N], ans, ansf, anss;
int main() {
	scanf("%d%d", &n, &m);
	for(int i = 1; i <= n; i++) scanf("%lld", &v[i]);
	for(int s = 2; s <= (m << 1); s++) {
		tmp[0] = 0; tmp[n + 1] = s - 1;
		for(int i = 1; i <= n; i++) tmp[i] = v[i] % s;
		sort(tmp, tmp + (n + 1) + 1);
		for(int i = 1; i <= n + 1; i++) {
			//a,b在 [tmp[i-1],tmp[i]]之间。 
			//fl: >=b 的个数是否为奇数。
			bool fl = (n + 1 - i) & 1;
			int l = max(tmp[i - 1], tmp[n - 1 + (!fl)] / 2) + 1, r = min(tmp[i], m);
			//是奇数:可能后手必败(先手必胜)。找次大 
			//是偶数:可能先手必败(后手必胜)。找最大 
			(fl ? ansf : anss) += max(0, min(r, s - l) - max(l, s - r) + 1);
		}
	} 
	ans = (1ll * m * m - ansf - anss) >> 1;
	printf("%lld %lld %lld %lld\n", ans, ans, ansf, anss);
	return 0;
}

标签:le,max,sum,Game,ge,win,情况,Chip,CF1033G
来源: https://www.cnblogs.com/zdsrs060330/p/16079421.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有