题意:给出n个集合,问这些集合能组合成几种不同的集合。
思路:枚举+状态压缩。由于1<=m<=14,所以最多有2^14=16 384种状态,每种状态可以存在一个int中。枚举所有的状态,运用位运算,判断能否由这n个集合组成。
#include<iostream>
using namespace std;
int main(){
int n, m, k, w, i, j;
int ans, val[105];
while(cin >> n >> m){
for(i = 0; i < n; i ++){
val[i] = 0;
cin >> k;
while(k --){
cin >> w;
val[i] |= 1<<(w-1);//把数字w存到val[i]的w位(从1开始)把1左移w-1位
}
}
ans = 0;
for(i = 1; i < (1<<m); i ++) // 枚举所有的状态。
for(w = j = 0; j < n; j ++)//枚举所有的val[j],如果是i子集,就加到w上,当w=i就ans++;
if((i|val[j]) == i){//val[j]是 i子集
w |= val[j];//把val[j]赋给w
if(w == i){
ans ++; break;
}
}
cout << ans << endl;
}
return 0;
}
时间: 2024-12-15 10:25:38