枚举s的子集
for(int i=s;i;i=(i-1)&s){
//具体操作
}
枚举大小为r的子集
for(int s=(1<<r)-1;s<1<<n;){
//具体操作
int x=s&-s;
int y=s+x;
s=((s&~y)/x>>1)|y;
}
转自:https://www.zhihu.com/question/68411978/answer/262980026
还有一种方法:
void GospersHack(int k, int n)
{
int cur = (1 << k) - 1;
int limit = (1 << n);
while (cur < limit)
{
// do something
int lb = cur & -cur;
int r = cur + lb;
cur = ((r ^ cur) >> __builtin_ctz(lb) + 2) | r;
// 或:cur = (((r ^ cur) >> 2) / lb) | r;
}
}
转自:https://zhuanlan.zhihu.com/p/360512296