zoukankan      html  css  js  c++  java
  • POJ 2443:Set Operation 经典位运算好题

    Set Operation
    Time Limit: 3000MS   Memory Limit: 65536K
    Total Submissions: 2965   Accepted: 1196

    Description

    You are given N sets, the i-th set (represent by S(i)) have C(i) element (Here "set" isn't entirely the same as the "set" defined in mathematics, and a set may contain two same element). Every element in a set is represented by a positive number from 1 to 10000. Now there are some queries need to answer. A query is to determine whether two given elements i and j belong to at least one set at the same time. In another word, you should determine if there exist a number k (1 <= k <= N) such that element i belongs to S(k) and element j also belong to S(k).

    Input

    First line of input contains an integer N (1 <= N <= 1000), which represents the amount of sets. Then follow N lines. Each starts with a number C(i) (1 <= C(i) <= 10000), and then C(i) numbers, which are separated with a space, follow to give the element in the set (these C(i) numbers needn't be different from each other). The N + 2 line contains a number Q (1 <= Q <= 200000), representing the number of queries. Then follow Q lines. Each contains a pair of number i and j (1 <= i, j <= 10000, and i may equal to j), which describe the elements need to be answer.

    Output

    For each query, in a single line, if there exist such a number k, print "Yes"; otherwise print "No".

    Sample Input

    3
    3 1 2 3
    3 1 2 5
    1 10
    4
    1 3
    1 5
    3 5
    1 10
    

    Sample Output

    Yes
    Yes
    No
    No
    

    Hint

    The input may be large, and the I/O functions (cin/cout) of C++ language may be a little too slow for this problem.

    题意是给出了N个的集合,一个集合中有若干个数。然后是Q个询问,两个数是否在一个集合中。

    发现一共最多就1000个集合,假设这个集合标号为N,那么能发现 h=N/32;k=N%32; h与k就可以对这个集合标号N进行标识了。所以用 a[h][j]= k 表示j这个数在 h*32 + (k二进制位为1的那个标识位) 这个集合中。

    然后询问两个数是否在一个集合中,只需询问在h相同的情况下,两个k1,k2相与是否大于0,大于0说明存在两个都是1的位置,就说明这两个数曾在一个集合中了。

    代码:

    #include <iostream>
    #include <algorithm>
    #include <cmath>
    #include <vector>
    #include <string>
    #include <cstring>
    #pragma warning(disable:4996)
    using namespace std;
    
    int a[32][10001];
    int n,q;
    
    int main()
    {
    	int i,j,f,h,k,num;
    	bool flag;
    	memset(a,0,sizeof(0));
    	scanf("%d",&n);
    	for(i=1;i<=n;i++)
    	{
    		scanf("%d",&f);
    		h=i%32;
    		k=i/32;
    		for(j=1;j<=f;j++)
    		{
    			scanf("%d",&num);
    			a[h][num] = a[h][num]|(1<<k);
    		}
    	}
    	scanf("%d",&q);
    	for(i=1;i<=q;i++)
    	{
    		scanf("%d%d",&h,&k);
    		flag=false;
    		for(j=0;j<32;j++)
    		{
    			if(a[j][h]&a[j][k])
    			{
    				flag=true;
    				break;
    			}
    		}
    		if(flag)
    			printf("Yes
    ");
    		else
    			printf("No
    ");
    	}
      
    	return 0;
    }
    


    版权声明:本文为博主原创文章,未经博主允许不得转载。

  • 相关阅读:
    C 语言高效编程的几招——A few action of efficient C language programming
    UDP套接字——(DGRAM)
    初学数位DP--hdu 2089
    leetcode Reverse Nodes in k-Group
    CC+语言 struct 深层探索——CC + language struct deep exploration
    [置顶] JDK工具(一)–Java编译器javac
    非归档数据文件offline的恢复
    [置顶] OpenJDK源码研究笔记(九)-可恨却又可亲的的异常(NullPointerException)
    MSF溢出实战教程
    一些安全名词解释
  • 原文地址:https://www.cnblogs.com/lightspeedsmallson/p/4899554.html
Copyright © 2011-2022 走看看