zoukankan      html  css  js  c++  java
  • CF1375F Integer Game

    CF1375F Integer Game
    三堆石子分别有 (a,b,c) 个,游戏规则:

    • 先手选择一个数 (k)
    • 后手把他加到任意一堆石子上,但不能连续对同一堆石子操作两次
    • 如果有两堆石子数量相同,先手赢;回合数超过 (1000),后手赢

    交互,自选先后手
    (a,b,cle 10^9,kle 10^{12})

    考虑先手赢的最后一部肯定是有局面 ((n-k,n,n+k)),并且上一步操作的是 (n+k),此时只要加上 (k) 即可
    或者说存在 (a+c=2b) 且上一步操作的是当前最大的那一堆

    考虑上一步要求操作的数是 (p),有局面 ((n-k,n,n+k-p))

    • 此时如果把 (p) 加到第一堆上,有 ((n-k+p,n,n+k-p)),发现只要有 (k<p),就仍然可以获胜(获胜需要 (n-k+p>n+k-p))
    • 此时如果把 (p) 加到第二堆上,有 ((n-k,n+p,n+k-p)),发现这样不太能必胜,于是此时需要让再上一步操作必定对第二堆进行

    考虑再上一步操作给出的是 (q),有局面 ((n-k,n-q,n+k-p))

    • 如果加到第一堆上,有 ((n-k+q,n-q,n+k-p))
      • 此时如果有 ((n-k+q)+(n+k-p)=2(n-q)) 可以是一种必胜情况,解出此时 (p=3q)
      • 另有要求 (n-k+q>n+k-p Rightarrow 2k<p+qRightarrow k<frac{2}{3}p)
    • 如果加到第三堆上,有 ((n-k,n-q,n+k-p+q))
      • 此时根据之前解的 (p=3q),仍然是一三堆的和是二堆的两倍
      • 但需保证 (n+k-p+q>n-kRightarrow k>frac{1}{3}p)

    现在若存在合理的 (n,k,p,q) 并且使得上面的条件全都满足,就逐个操作 (q,p,k) 即可,整理出条件是:

    [egin{cases} a=n-k\ b=n-q\ c=n+k-p\ p=3q\ k<frac{2}{3}p\ k>frac{1}{3}p\ end{cases}]

    这样根据前面几个等式解出来就是

    [egin{cases} n=3b-2a-c\ q=2b-a-c\ k=3b-2a-c\ end{cases}]

    此时只要钦定 (b>c> a),即可满足两个不等式

    long long aa,bb,cc;
    inline void change(int o,long long p){
    	if(!o) exit(0);
    	else if(o==1) aa+=p;
    	else if(o==2) bb+=p;
    	else if(o==3) cc+=p;
    }
    inline int fuck(){
    	int ff=0;
    	if(aa+bb==(cc<<1)) printf("%lld
    ",lib::max(aa,bb)-cc),ff=1;
    	else if(aa+cc==(bb<<1)) printf("%lld
    ",lib::max(aa,cc)-bb),ff=1;
    	else if(bb+cc==(aa<<1)) printf("%lld
    ",lib::max(bb,cc)-aa),ff=1;
    	if(ff) return fflush(stdout),1;
    	return 0;
    }
    int main(){
    	long long a=read(),b=read(),c=read();
    	aa=a;bb=b;cc=c;
    	if(a>c) lib::swap(a,c);
    	if(c>b) lib::swap(b,c);
    	if(a>c) lib::swap(a,c);
    	if(c>b) lib::swap(b,c);
    	if(a>c) lib::swap(a,c);
    	if(c>b) lib::swap(b,c);
    	if(a>c) lib::swap(a,c);
    	if(c>b) lib::swap(b,c);
    	long long n=3*b-a-c,k=3*b-2*a-c,q=2*b-a-c,p=q*3;
    	puts("First");fflush(stdout);
    	printf("%lld
    ",q);fflush(stdout);
    	change(read(),q);
    	if(fuck()) return 0;
    	printf("%lld
    ",p);fflush(stdout);
    	change(read(),p);
    	if(fuck()) return 0;
    	printf("%lld
    ",k);fflush(stdout);
    	assert(fuck());
    	return 0;
    }
    
  • 相关阅读:
    MS SQL2000 && 2005转出数据字典
    基于角色的访问控制'的权限管理的数据库的设计实现
    ANSI SQL / T SQL / PLSQL
    MS SQL系統資料表內容
    关闭不需要服务 为Windows系统提速
    Form.Enctype屬性
    流程圖
    ASPSmartUpload祥解
    数据排序常见算法(JS版)
    如何实现定时开机
  • 原文地址:https://www.cnblogs.com/suxxsfe/p/15497102.html
Copyright © 2011-2022 走看看