考点:线段树求最大值
思路:本质为求l[i]最大值,使得两个数异或和为x成立
//1.a^b=x,则x^b=a,即异或的可逆性
//2.转化为求a[i]左边第一个数a[j],令a[j]^a[i]=x,得到l[i]
//3.转化为求区间最大值题目
#include <bits/stdc++.h>
#define ll long long
using namespace std;
ll n,m,x;
ll a[200005],b[200005],p[2000005];
ll tree[400005];
void build(ll o, ll l, ll r)
{
if (l == r)
{
tree[o] = a[l];
return;
}
ll mid = (l + r) / 2;
build(2*o, l, mid);
build(2*o+1, mid + 1, r);
tree[o]=max(tree[2*o],tree[2*o+1]);
}
ll query(ll o, ll l, ll r, ll x, ll y)
{
if (x <= l && r <= y)
return tree[o];
ll max1=0;
ll mid=(l+r)/2;
if(mid>=x)max1=max(max1,query(2*o,l,mid,x,y));
if(mid<y)max1=max(max1,query(2*o+1,mid+1,r,x,y));
return max1;
}
int main()
{
cin>>n>>m>>x;
for(ll i=1;i<=n;i++)
scanf("%lld",&b[i]);
ll c;
ll j;
memset(p,0,sizeof(p));
for(int i=1;i<=n;i++)
{ a[i]=p[b[i]^x];
p[b[i]]=i;
}
build(1,1,n);
for(ll i=1;i<=m;i++)
{
ll l1,r1; scanf("%lld %lld",&l1,&r1);
ll as=query(1,1,n,l1,r1);
if(as>=l1)printf("yes\n");
else printf("no\n");
}
}