题目链接:http://codeforces.com/contest/1174/problem/D
题目大意:给你一个n,让你用[1, 2^n)的数来构造一个序列。使序列尽量长。
要求:没有子序列的异或=0或者x。
思路:直接构造这个序列很难,根据异或的知识
sum[i]:异或的前缀和:sum[i]=a[1]^a[2]^...^a[i]
1.如果这个子序列异或=0, 那么sum[x]==sum[y]
2.如果这个子序列异或=x, 那么sum[x]^x==sum[y]
这样我们就可以知道前缀和:不能重复,并且前缀和异或!=x。而且前缀和<2^n。
并且前缀和只能出现(2^n-2)/2个
那么我们可以构造前缀和:每次标记不能出现的前缀和。然后通过前缀和来得到a[i]就可以了。
#include<bits/stdc++.h>
#define LL long long
using namespace std;
int vis[(1<<18)+10]={0};
vector<int> v;
int main()
{
int n, x;
scanf("%d%d",&n,&x);
vis[x]=1;
v.push_back(0);
for(int i=1;i<(1<<n);i++)
{
if(vis[i])
{
continue;
}
v.push_back(i);
vis[i]=1;
vis[i^x]=1;
}
printf("%d\n",v.size()-1);
for(int i=1;i<v.size();i++)
{
printf("%d ",v[i]^v[i-1]);
}
return 0;
}