二进制枚举模版

模拟写法

枚举子集

#include<bits/stdc++.h>
using namespace std;
int main()
{
	int n;
	int b[100];
	cin>>n;
	for(int i=0; i<=n; i++)b[i]=0;
	while(b[0]==0){
		for(int i=1; i<=n; i++)cout<<b[i];
		cout<<"\n";
		int j=n;
		while(b[j]==1)
			j--;
		b[j]++; 
		for(int i=j+1; i<=n; i++)b[i]=0; 
	} 

	return 0;
}

组合输出

#include<bits/stdc++.h>
using namespace std;

int main()
{
	int n, r;
	int b[100];
	cin>>n>>r;
	for(int i=1; i<=n; i++)b[i]=i;
	b[0]=-1;
	while(b[0]==-1){
		for(int i=1; i<=r; i++)cout<<b[i]<<" ";
		cout<<"\n";
		int j=r; 
		while(b[j]==n-r+j)j--;
		b[j]++;
		for(int i=j+1; i<=r; i++)b[i]=b[i-1]+1;
	} 

	return 0;
}

位运算写法

枚举子集

#include<bits/stdc++.h>
using namespace std;
int a[10];
void print_subset(int n)
{
    for(int i=0; i<(1<<n); i++){
        for(int j=0; j<n; j++)
            if(i&(1<<j))
                cout<<a[j]<<" ";
        cout<<endl;
    }
}
int main()
{
    int n;
    cin>>n;
    for(int i=0; i<n; i++)a[i]=i+1;//初始化数组
    print_subset(n);
    return 0;
 }

组合输出

#include<bits/stdc++.h>
using namespace std;
int a[10];
void print_subset(int n, int m)
{
    for(int i=0; i<(1<<n); i++){
        int num=0, kk=i;//num统计i中1的个数;kk用来处理i
        while(kk){
            kk=kk&(kk-1);//清除kk中的最后一个1
            num++;//统计1的个数
        }
        if(num==m){//二进制数中的1有k个,符合条件
            for(int j=0; j<n; j++)
                if(i&(1<<j))
                    cout<<a[j]<<" ";
            cout<<endl;
        }
    }
}
int main()
{
    int n, m;
    cin>>n>>m;
    for(int i=0; i<n; i++)a[i]=i+1;//初始化数组
    print_subset(n, m);
    return 0;
 }

除了以上写法还可以使用dfs写法
时间复杂度均为指数级别,使用于数据规模在20左右的暴力枚举

posted @ 2022-12-03 11:37  TFLSNOI  阅读(39)  评论(0编辑  收藏  举报