计蒜客 A1607 UVALive 8512 [ACM-ICPC 2017 Asia Xi'an]XOR


ICPC官网题面假的,要下载PDF,点了提交还找不到结果在哪看(我没找到),用VJ交还直接return 0;也能AC
计蒜客题面 这个好

  • Time limit 3000 ms
  • OS Linux
  • 题目来源 ACM-ICPC 2017 Asia Xi'an

VJ爬到的英文题面什么鬼啊,除了标题,哪里有xor字样啊?\((A[i_1], A[i_2], . . . , A[i_t])\)意思是gcd啊?简直了。

计蒜客的题面

2000ms 是不是计蒜客评测姬快一点,时限少了1s
262144K

Consider an array \(A\) with n elements . Each of its element is \(A[i] (1≤i≤n)\) . Then gives two integers \(Q, K\), and \(Q\) queries follow . Each query , give you$ L, R$, you can get \(Z\) by the following rules.

To get \(Z\) , at first you need to choose some elements from \(A[L]\) to \(A[R]\) ,we call them \(A[i_1],A[i_2]…A[i_t]\) , Then you can get number \(Z=K \text{or} (A[i_1] \text{xor} A[i_2] … \text{xor} A[i_t])\) .

Please calculate the maximum \(Z\) for each query .

Input

Several test cases .

First line an integer \(T (1≤T≤10)\) . Indicates the number of test cases.Then \(T\) test cases follows . Each test case begins with three integer \(N, Q, K (1≤N≤10000, 1≤Q≤100000, 0≤K≤100000)\) . The next line has \(N\) integers indicate \(A[1]\) to \(A[N] (0≤A[i]≤10^8)\). Then \(Q\) lines , each line two integer \(L, R (1≤L≤R≤N)\) .

Output

For each query , print the answer in a single line.

样例输入

1
5 3 0
1 2 3 4 5
1 3
2 4
3 5

样例输出

3
7
7

解题思路

再扔个链接

和todolist的之前一题差不多,也是用线段树维护区间线性基,线段树上每个点都是对应区间的线性基。这题时间空间稍微宽松一些了,所以十分暴力,不加各种优化也可以0ms轻松AC。或上k的问题,可以在输入时把A里所有元素处理一下:a[i]&=~k;,把k为1那几位全部清零,输出的时候找处理后的区间异或最大值,在或上k即可。正确性还不会证,留坑。但意会一下感觉是对的。

又完成了一份todolist

  • [x] CodeForces 1100F 单纯询问区间异或最大值
  • [x] HDU 6579 多了个末尾插入数据的操作,还有强制在线
  • [x] BZOJ 4184 这题还多了插入和删除的操作。居然是权限题……本地测一下算了。
  • [x] UVALive 8514 2017ICPC西安的一道题,操作都差不多

源代码

#include
#include
#include


const int MAXN=1e4+5;

int T;
int n,q,k;

struct Linear{
	std::vector p;//32就够了
	void insert(int x)
	{
		if(p.size()>=32) return;
		for(int i=p.size()-1;~i;i--)
		{
			if((x^p[i])>1;
	build(x<<1,l,mid);
	build(x<<1|1,mid+1,r);
	t[x]=t[x<<1];
	t[x].merge(t[x<<1|1]);
}
Linear ans;
void que(int x,int l,int r,int ql,int qr)//每次询问前要在主函数中清空ans//会内存泄漏吗……
{
	if(ql<=l&&r<=qr)
	{
		ans.merge(t[x]);
		return;
	}
	int mid=l+r>>1;
	if(ql<=mid) que(x<<1,l,mid,ql,qr);
	if(qr>mid) que(x<<1|1,mid+1,r,ql,qr);
}

int main()
{
	scanf("%d",&T);
	while(T--)
	{
		scanf("%d%d%d",&n,&q,&k);
		k=~k;
		for(int i=1;i<=n;i++)
		{
			scanf("%d",a+i);
			a[i]&=k;
		}
		k=~k;
		build(1,1,n);
		while(q--)
		{
			int l,r;
			scanf("%d%d",&l,&r);
			ans=ze;
			que(1,1,n,l,r);
			printf("%d\n",ans.quemx()|k);
		}
	}
	return 0;
}