EOJ Monthly 2019.9 (based on September Selection) A.才艺展示(博弈sg找规律)、D.站军姿(概率)

A. 才艺展示(sg找规律)

题目

Cuber QQ 和 Little Fang 两人会按照游戏规则轮流写 { 1,2,⋯,N } ( N 是一个正整数)中的一个数。

游戏的规则是这样的,若一个人写下数 i , 则另一个人只能写 i+1 或 2i ( i,i+1,2i 均不超过 N )。两个人中,谁先写到 N 这个数字,谁就能获胜。

当然 Cuber QQ 为了表现自己的绅士,他让 Little Fang 先写, Little Fang 的开场是单调而固定的,他一定会写数字 1 。

由于表演需要,两个人一共要玩 T 局游戏。每局游戏都会给定提前正整数 N ,当然 Cuber QQ 和 Little Fang 的聪明程度是毋庸置疑的,所以他们都会按照最优的策略进行游戏。

1<=T<=1e5,1<=N<=1e18

思路来源

涛神

题解

先sg打个表

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
using namespace std;
const int N=1005;
int n;
int ok[N];
int dfs(int i)
{
	if(~ok[i])return ok[i]; 
	if(i==n)return ok[i]=0;//是否必败 
	bool f=1;//是否必败 
	if(i+1<=n)f&=dfs(i+1);
	if(2*i<=n)f&=dfs(2*i);
	ok[i]=f^1;
	return ok[i];
}
void out(int x)
{
	int s[10],cnt;
	for(;x;x/=2)
	s[++cnt]=x%2;
	reverse(s+1,s+cnt+1);
	for(int i=1;i<=10-cnt;++i)
	printf("%d",0);
	for(int i=1;i<=cnt;++i)
	printf("%d",s[i]);
	puts(""); 
}
int main()
{
	for(int i=1;i<=1000;++i)
	{
		n=i;
		memset(ok,-1,sizeof ok);
		if(dfs(1))
		{
			printf("%-10d:",n);
			out(i);
		}
	}
	return 0;
}

看前面看不出来,转化成二进制(i->2*i)发现,

后手必胜当且仅当二进制位只有偶数位能为1

代码

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
using namespace std;
typedef long long ll;
int T;
ll n,lose;
int main()
{
	for(int i=0;i<64;i+=2)
	lose|=(1ll<<i);
	scanf("%d",&T);
	while(T--)
	{
		scanf("%lld",&n);
		if(n&lose)puts("Little Fang Win");
		else puts("Cuber QQ Win");
	}
	return 0;
}

和涛神讨论了一下证明:

①n%2==1 先手必胜 n=2*i+1 先手可以控制不去2*i这个状态从而获胜 

由于2*i这个状态是偶数 先手位于1 不管后手怎么取 后手选完之后的数都是偶数 

先手每次都+1就保持奇数状态 从而让对手去2*i 从而先手必胜 

②n与4*n走到的人相同,故二者胜负情况相同,若A走到n,分两种情况,

(1)B走到2*n,此时A可走到4*n

(2)B走到n+1,此时A可走到2*n+2,由于剩下无法*2,+1交替知A走到4*n

③4*n与4*n+2胜负情况相同,只需证4n+2只能由4n通过+1+1得,不能通过(2*n+1) *2得即可

显然2*n+1只能通过2*n转移得来,若A走到2*n,B走到2n+1,则A走到4*n+2,A获胜

同理,所以在A走到2*n时,B不会走+1,只会*2到4*n,所以4*n+2与4*n同胜负

④n==2时,后手获胜

①到④可证明,后手获胜的情况,

只能是2,或2乘4若干次,或2乘4若干次再+2

这与前面sg打表的情况一致

 

D. 站军姿

题意

样例数T<=1e5

把n(n<=1e18)个点放在一个圆周上,问他们在同一个半圆周上的概率p/q(mod 1e9+7)

题解

圆中四鸭扩展版,结论题,答案为\frac{2n}{2^n}

考虑一只鸭子的选点,其覆盖域是一个半圆,那么把它覆盖的和没覆盖的两个半圆中间画一条线,

用这一条线代表这一只鸭子,鸭子可以选在这一条线的任意一侧,

n只鸭子2选1,共2^{n}种选法,而每一只鸭子都可以选择两点中的一点覆盖半圆,

n个半圆的交集的所有可能,构成了分子的解答,而n条不重合的线将圆分成2n条弧

每一条弧都对应了一种不同情况的交集,故为上述结论

 

后续:感觉官方题解更好理解

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Code92007

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值