Codeforces Round #717 (Div. 2)-B. AGAGA XOOORRR-题解
Posted Tisfy
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Codeforces Round #717 (Div. 2)-B. AGAGA XOOORRR-题解相关的知识,希望对你有一定的参考价值。
目录
Codeforces Round #717 (Div. 2)-B. AGAGA XOOORRR
传送门
Time Limit: 1 second
Memory Limit: 256 megabytes
Problem Description
Baby Ehab is known for his love for a certain operation. He has an array a a a of length n n n, and he decided to keep doing the following operation on it:
Now he asks you if he can make all elements of the array equal. Since babies like to make your life harder, he requires that you leave at least 2 2 2 elements remaining.
Input
The first line contains an integer t t t ( 1 ≤ t ≤ 15 1 \\le t \\le 15 1≤t≤15) — the number of test cases you need to solve.
The first line of each test case contains an integers n n n ( 2 ≤ n ≤ 2000 2 \\le n \\le 2000 2≤n≤2000) — the number of elements in the array a a a.
The second line contains n n n space-separated integers a 1 a_1 a1, a 2 a_2 a2, … \\ldots …, a n a_{n} an ( 0 ≤ a i < 2 30 0 \\le a_i < 2^{30} 0≤ai<230) — the elements of the array a a a.
Output
If Baby Ehab can make all elements equal while leaving at least 2 2 2 elements standing, print “YES”. Otherwise, print “NO”.
Sample Input
2
3
0 2 2
4
2 3 1 10
Sample Onput
YES
NO
Note
In the first sample, he can remove the first 2 2 2 elements, 0 0 0 and 2 2 2, and replace them by 0 ⊕ 2 = 2 0 \\oplus 2=2 0⊕2=2. The array will be [ 2 , 2 ] [2,2] [2,2], so all the elements are equal.
In the second sample, there’s no way to make all the elements equal.
题目大意
给你 n n n个数,你可以选择其中的任意两个进行异或操作,这样两个数就变成了一个数。
问你能不能使这 n n n个数最终的异或结果为不少于 2 2 2个的相同的数。
解题思路
首先要明白几个数相互异或,不论顺序如何,最终结果是不受影响的。
同时,两个相同的数异或结果是 0 0 0。
我们可以先让所有的这 n n n个数全部异或,得到一个结果。
如果这个结果是 0 0 0,就说明得到 0 0 0这个结果的上一步是两个相同的数,即,只有两个相同的数异或才能得到 0 0 0。这样就说明可以找到一种异或顺序,使得最终异或结果是两个相等的数。就直接输出YES
即可。
否则,如果结果想要是YES
,就必须至少能异或成 3 3 3个相同的数(题目说了不能是 1 1 1个相同的数)。
这 3 3 3个相同的数异或得到的结果就是所有数异或得到的结果。
于是我们就从头开始异或,直到得到这个最终的异或结果,这就得到了三个数中的一个数。从下一个数开始逐个异或,知道可以再得到一个与最终结果相同的数为止,我们就得到了三个数中的第二个。剩下的数全部异或起来一定是结果这个数。这样的话就输出YES
。
如果有同学想问为什么输出YES
的话,最终结果一定可以是
2
2
2个或
3
3
3个相同的数,而不是
4
4
4个或
5
5
5个呢?那么请看下面:
假设最终我们能够得到 4 4 4个相同的数,那么我们把这 4 4 4个相同的数分成两组,一组有两个数。则每组的两个数异或,原本的 4 4 4个数就变成了异或后的 2 2 2组。所以如果能最终能得到 4 4 4个相同的数,就一定能得到 2 2 2个相同的数。
同理,如果能分成 5 5 5组,就选其中的 3 3 3个数相异或变成一个数,就得到了相同的 3 3 3个数。所以如果最终能得到 5 5 5个相同的数,就一定能得到 3 3 3个相同的数。
如果还不太懂可以看看代码:
AC代码
#include <bits/stdc++.h>
using namespace std;
#define mem(a) memset(a, 0, sizeof(a))
#define dbg(x) cout << #x << " = " << x << endl
#define fi(i, l, r) for (int i = l; i < r; i++)
#define cd(a) scanf("%d", &a)
typedef long long ll;
int a[2020];
void solve()
{
int n;
cin>>n;
int res=0;//所有的数全部异或起来,最终结果是res
fi(i,0,n)//for(int i=0;i<n;i++)
{
cd(a[i]);//scanf("%d", &a[i]);
res^=a[i];//res异或上a[i]
}
if(res==0)//如果最终结果是0,那么得到0的上一步一定是两个相同的数
{
puts("YES");//所以我们可以直接输出YES并退出
return;
}
int s=0;//一些数异或起来得到的结果
int loc=0;//下标从第一个数开始
for(loc=0;loc<n;loc++)
{
s^=a[loc];//异或上a[i]
if(s==res)break;//如果前面一些数异或得到的结果已经是最终答案了,就找到了这3个数中的一个,就退出。
}
if(loc>=n-2)//如果不能再找到两个相同的数
{
puts("NO");//输出NO
return;
}
loc++;//下标从下一个未异或过的数开始
s=0;//一串异或起来的结果
for(;loc<n-1;loc++)
{
s^=a[loc];//异或上a[loc]
if(s==res)break;//如果结果是最终结果,就找到了第二个数
}
if(s!=res)//如果这一串异或起来不是最终结果
{
puts("NO");//就不行
return;
}
loc++;//从下一个数开始异或
s=0;//第三串异或的结果
for(;loc<n;loc++)//这次要异或到最后
{
s^=a[loc];//异或上a[loc]
}
if(s==res)//如果第3串异或的结果也是最终结果
puts("YES");//可以
else//否则
puts("NO");//不行
return;
}
int main()
{
int N;
cin>>N;//N组测试样例
while(N--)
{
solve();
}
return 0;
}
如果哪里看不懂可以在下面评论留言
原创不易,转载请附上原文链接哦~
Tisfy:https://letmefly.blog.csdn.net/article/details/116354549
以上是关于Codeforces Round #717 (Div. 2)-B. AGAGA XOOORRR-题解的主要内容,如果未能解决你的问题,请参考以下文章
Codeforces Round #717 (Div. 2)-A. Tit for Tat-题解
区间倍增dpD. Cut——Codeforces Round #717 (Div. 2)
Codeforces Round #717 (Div. 2)-C. Baby Ehab Partitions Again-题解
Codeforces Round #717 (Div. 2)-B. Maximum Cost Deletion-题解
Codeforces Round #717 (Div. 2)-B. Maximum Cost Deletion-题解
Codeforces Round #717 (Div. 2)-C. Baby Ehab Partitions Again-题解