题目描述
 小a有n个数,他提出了一个很有意思的问题:他想知道对于任意的x, y,能否将x与这n个数中的任意多个数异或任意多次后变为y
输入描述:
 第一行为一个整数n,表示元素个数
 第二行一行包含n个整数,分别代表序列中的元素
 第三行为一个整数Q,表示询问次数
 接下来Q行,每行两个数x,y,含义如题所示
 输出描述:
 输出Q行,若x可以变换为y,输出“YES”,否则输出“NO”
示例1
 输入
5
 1 2 3 4 5
 3
 6 7
 2 1
 3 8
输出
YES
 YES
 NO
说明
 对于(6,7)来说,6可以先和3异或,再和2异或
 对于(2,1)来说,2可以和3异或
 对于(3,8)来说,3不论如何都不能变换为8
 备注:
 对于100%的数据,n,Q<=105
 保证所有运算均在int范围内
很明显的线性基了,利用线性基的性质,我们可以知道看一个数字是否可以被原序列异或得到,那么就是看这个数字能否被线性基异或得到(异或转换一下,两边同时异或x,所以check x^y ),我们check一下即可。
AC代码:
#pragma GCC optimize(2)
#include<bits/stdc++.h>
#define int long long
using namespace std;
const int N=1e5+10;
int n,q,a[N],d[50];
inline void get_lb(int x){
	for(int i=31;i>=0;i--){
		if(!(x>>i))	continue;
		if(!d[i]){
			d[i]=x;	break;
		}else	x^=d[i];
	}
}
inline int check(int x){
	for(int i=31;i>=0;i--){
		if(!(x>>i))	continue;
		x^=d[i];
	}
	return x==0;
}
signed main(){
	cin>>n;
	for(int i=1;i<=n;i++)	cin>>a[i],get_lb(a[i]);
	cin>>q;
	while(q--){
		int x,y;	cin>>x>>y;
		if(check(y^x))	puts("YES");
		else	puts("NO");
	}
	return 0;
}

京公网安备 11010502036488号