POJ2443 Set Operation - bitset

4 篇文章 0 订阅

题意:给出n个集合(n<=1000),每个集合中最多有10000个数,数的范围:1~10000,给出q个询问(q<=200000),每次给出两个数a,b判断是否有一个集合中同时含有a,b两个数

因为集合数少而集合所含的数多,在位运算时若加快速度,就要减少bitset存的位置
所以我们开10000个bitset,每个bitset存数字i所在哪个集合,比如集合1,2,3中都有数字5,但是集合4中没有,那么bitset[5] = 1110,而bitset只需开到1000位以上
这样给我们两个数的时候,只要把他们的bitset按位与一下即可

#include <algorithm>
#include <iostream>
#include <cstring>
#include <cstdio>
#include <bitset>
using namespace std;
const int MAXN = 10000 + 10;
int n,m,q,ans;
bitset<1010> temp, bit[MAXN];
int main() {
    while(scanf("%d", &n) != EOF) {
        for(int i=1; i<=n; i++) {
            bit[i].reset();
        }
        for(int i=1; i<=n; i++) {
            int snum;
            scanf("%d", &snum);
            for(int j=1; j<=snum; j++) {
                int ai;
                scanf("%d", &ai);
                bit[ai][i] = 1;
            }
        }
        scanf("%d", &q);
        for(int i=1; i<=q; i++) {
            int a,b;
            scanf("%d %d", &a, &b);
            temp = bit[a] & bit[b];
            if(temp.count()) printf("Yes\n");
            else printf("No\n");
        }
    }
    return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值