首页 > 其他分享 >2024.10.14 Codeforces Round 978 (Div. 2)

2024.10.14 Codeforces Round 978 (Div. 2)

时间:2024-10-29 21:47:28浏览次数:6  
标签:卧底 14 int 询问 2024.10 Codeforces 如果 问到 2k

比赛链接

Solved:4/7

Upsolved:5/7

Rank:447(rated 343)


D2. Asesino(Hard Version)

题意:

有 n 个人,除了一个卧底以外,其他人或者只会说真话,或者只会说谎,且他们知道彼此的身份。卧底只会说谎,但其他人都认为他只会说真话。现在你可以进行若干次询问,每次询问形如问第 i 个人第 j 个人是什么身份。现在要用最少的询问次数找到这个卧底。这里的最少指:你的询问次数不能超过“能保证在给定n的任何情况下都可以找到卧底”的询问次数。

做法:

首先注意到如果a和b都不是卧底,那么问(a,b)和问(b,a)得到的回答应该相同。

所以当n为偶数时,每次问(2k-1,2k),如果回答不同,那么卧底就在两人之间。这时再随便找一个人(此时其他人都必不是卧底),问(2k-1,x)和(x,2k-1)。若回答仍然不同,则2k-1是卧底;否则2k是卧底。

注意如果问到n-2仍然没问到卧底,那么卧底一定在n-1和n之间,此时不用再浪费两次机会,直接确定n-1是不是卧底即可。总次数为n。

当n为奇数时,如果和偶数一样做,如果问到n-1都没问到,最后会剩一个人,答案就是n-1;如果问到n-3之前就问到了,答案小于n。但唯一问题在于:如果卧底在n-2和n-1之间,那么还需要2次机会来确定卧底,总共将需要n+1次。有什么方法去掉多出来的1次吗?

n=3时,不管怎么试都至少需要4次。

n≥5为奇数时,可以注意到另一个性质:确定三个人都不是卧底只需要三次询问——问(a,b),(b,c),(c,a),如果这三次询问的异或和为1,那么他们一定都不是卧底。

因此先问 12,23,31 确定卧底是否在 123 中。如果在,那么再问 13 和 21 进一步确定卧底是谁。如果不在,和偶数一样做。剩两个人时直接问 (1,n) 和 (n,1)。这样还是只需要n次。

int n;
int qry(int x,int y){
    cout<<"? "<<x<<' '<<y<<endl;
    int res;
    cin>>res;
    return res;
}
void solve(){
    cin>>n;
    if(n==3){
        int x=qry(1,2),y=qry(2,1);
        if(x==y){cout<<"! "<<3<<endl;return;}
        else{
            int u=qry(1,3),v=qry(3,1);
            if(u==v){cout<<"! "<<2<<endl;return;}
            else{cout<<"! "<<1<<endl;return;}
        }
    }
    if(n&1){
        int u=qry(1,2),v=qry(2,3),w=qry(3,1);
        if(!(u^v^w)){
            int z=qry(1,3);
            if(z!=w){
                int t=qry(2,1);
                if(u==t){cout<<"! "<<3<<endl;return;}
                else{cout<<"! "<<1<<endl;return;}
            }
            else{cout<<"! "<<2<<endl;return;}
        }
        else{
            if(n==5){
                int u=qry(1,4),v=qry(4,1);
                if(u==v){cout<<"! "<<5<<endl;return;}
                else{cout<<"! "<<4<<endl;return;}
            }
            else{
                for(int i=4;i+3<=n;i+=2){
                    int x=qry(i,i+1),y=qry(i+1,i);
                    if(x!=y){
                        int u=qry(i,1),v=qry(1,i);
                        if(u!=v){cout<<"! "<<i<<endl;return;}
                        else{cout<<"! "<<i+1<<endl;return;}
                    }
                }
                int u=qry(1,n),v=qry(n,1);
                if(u==v){cout<<"! "<<n-1<<endl;return;}
                else{cout<<"! "<<n<<endl;return;}
            }
        }
    }
    for(int i=1;i+3<=n;i+=2){
        int x=qry(i,i+1),y=qry(i+1,i);
        if(x!=y){
            int u=qry(i,n),v=qry(n,i);
            if(u!=v){cout<<"! "<<i<<endl;return;}
            else{cout<<"! "<<i+1<<endl;return;}
        }
    }
    int u=qry(1,n),v=qry(n,1);
    if(u!=v){cout<<"! "<<n<<endl;return;}
    else{cout<<"! "<<n-1<<endl;return;}
}

怎么证明小于n一定不能保证呢?

标签:卧底,14,int,询问,2024.10,Codeforces,如果,问到,2k
From: https://www.cnblogs.com/EssentialSingularity/p/18514588

相关文章

  • 2024.10.24 The 2021 ICPC Northwestern Russia Regional Contest
    比赛链接Solved:8/14Penalty:909Rank:23前五道签到题ABCHL。K.KaleidoscopicRoute题意给一张带边权的图,求一条1到n的路径,使经过的边数最少的同时边的极差最大。题解求出最短路图,然后DAG上dp:f和g分别表示从1到这个点能经过的最大边权和最小边权。然后每转移一条边(x,y,z......
  • 2024.10.4 2018-2019 ACM-ICPC Southeastern European Regional Programming Contest
    比赛链接Solved:7/11Penalty:914Rank:1/74Rank(vp):63/1k+Dirt:22%G答案是4*纯色块数+5。考虑怎么维护这个纯色块数。这道题的修改保证了一个块纯色当且仅当其行列都纯色。因此对行列分别维护一棵线段树,维护每一层分别有多少个纯色节点,按层乘起来相加就行。K1操作的增加量......
  • 2024.10.3 2022-2023 ICPC Brazil Subregional Programming Contest
    比赛链接Solved:12/14Rank:5/1k+Rank(vp):49/2k+Penalty:1619Dirt:45%前10个题都比较简单/套路。L做法很好想。但是……因为不会写启发式合并卡了40min,警钟长鸣!intsum[N];map<int,int>col[N];intsz[N];llnow[N],ans[N];voidmrg(intx,inty){x=find(x),y=fi......
  • 2024.10.26 2024 CCPC哈尔滨站
    Solved:6/13Penalty:635Rank:72Rank(ucup):170打到后面困了(而且不会L心态爆炸)睡觉去了,不然还能多做个E题(被L单防了啊。。CGKM:签到,不放了。J.NewEnergyVehicle$n$种汽油,$m$个加油站,每个加油站只能加一种油,每种油都是一单位能走一公里,求最远能走多少公里。$n,m\leq......
  • 2024.10.29 test
    A已知\(n\)边形的一个三角剖分,你可以进行若干次“城市建造”操作,可以选择三个点并新建一个点为这三个点的内心并连边。构造方案,使得城市建造次数最少,且新图可以划分为两棵树。只需要进行一次城市建造操作,就可以使边数变为\(2n\),点数为\(n+1\),显然即可划分。考虑取出一个三......
  • 代码随想录day14 二叉树(2)
    文章目录day11栈与队列(2)栈与队列的总结day13二叉树(1)day14二叉树(2)day11栈与队列(2)逆波兰表达式求值https://leetcode.cn/problems/evaluate-reverse-polish-notation/逆波兰表达式,也就是后缀表达式,所谓后缀就是指运算符写在后面。平常使用的算式则是一种......
  • 2024.10.29
    1.reverse函数:翻转对于数组a,a+n;对于字符串或者向量a.begin(),a.end();具体在https://blog.csdn.net/YMWM_/article/details/1154682972.字符串的一种赋值方式点击查看代码for(inti=0;i<n;i++)s[i]=string(7*n/2,'')其中s[]=string(数量,'')是说将s[]这一行赋值为......
  • 题解:P8245 [COCI2013-2014#3] PAROVI
    题意定义两个整数\(A,B\)之间的距离为这两个整数所有对应位上的数的差的绝对值之和,记为\(\operatorname{dist}(A,B)\)。特别地,如果\(A,B\)两数的位数不相同,则在位数较小的数前补足前导\(0\)。现在,给定两个整数\(L,R\),请你求出所有在区间\([L,R]\)内的整数对的距离和。......
  • 学期2024-2025-1 学号20241424 《计算机基础与程序设计》第6周学习总结
    学期2024-2025-1学号20241424《计算机基础与程序设计》第6周学习总结作业信息这个作业属于哪个课程2024-2025-1-计算机基础与程序设计)这个作业要求在哪里(如2024-2025-1计算机基础与程序设计第六周作业这个作业的目标<参考上面的学习总结模板,把学习过程通过博客......
  • Educational Codeforces Round 171 (Rated for Div. 2) 题解(A-C)
    EducationalCodeforcesRound171(RatedforDiv.2)题解(A-C)这场ABC全都犯病了(悲伤)目录EducationalCodeforcesRound171(RatedforDiv.2)题解(A-C)目录A.PerpendicularSegmentsB.BlackCellsC.ActionFiguresA.PerpendicularSegments大意给你一个......