首先,^最小是1,怎么样才能是1呢,一定是两个数字仅仅1位不一样,比如(1,0) 、(10,11);但是未必所以都能满足1,不过即使不能满足1,如10,100也是相对于(11,110)而言比较小的,所以一位不同这一点保留,另外如果a^b=c,那么c^b=a,原因的话,^是相同为0,不同位1,假设第一个数字是(a+c),第二个数字是(b+c),这两个数字相同的部分是c,^之后a和b的部分都会1,其他变成0,其实就是a+b,那如果(a+c)^(a+b)就等于(b+c)。 其次,这是一个排列,所以数字不能一样 所以,我们可以设a0=0,从a1开始循环,里面套一个循环:从最低一位开始,把第一位变成1,其他位都是0,将这个数字与a[i-1]异或。如果得到数字a之前没有出现过,就将ai=a,否则加一位,再异或,得出最小的异或值
#include<bits/stdc++.h>
using namespace std;
#define int long long
signed main()
{
int n;cin>>n;
vector<int> visd(1<<n,0);
int front=0;visd[0]=true;
for(int i=1;i<(1<<n);i++)
{
cout<<front<<" ";
for(int j=0;j<n;j++)
{
int t=1<<j;
t=front^t;
if(!visd[t])
{
visd[t]=true;
front=t;
break;
}
}
}
cout<<front;
return 0;
}
其实是建议vector开大一点的,不过这题的话是一定会把2的n次方里所以的数字都放进去的,所以也没关系,因为每次只有一个1不同,所以是历遍全部的

京公网安备 11010502036488号