zoukankan      html  css  js  c++  java
  • [BZOJ2844]线性基+xor本质不同第K大

    https://blog.csdn.net/qq_39759315/article/details/88789872?depth_1-utm_source=distribute.pc_relevant.none-task-blog-BlogCommendFromBaidu-4&utm_source=distribute.pc_relevant.none-task-blog-BlogCommendFromBaidu-4

    https://blog.csdn.net/qq_39759315/article/details/88553043?depth_1-utm_source=distribute.pc_relevant.none-task-blog-BlogCommendFromBaidu-6&utm_source=distribute.pc_relevant.none-task-blog-BlogCommendFromBaidu-6

    input
    4
    1
    2
    12
    13
    13
    output
    11


    拿这个样例来说,构成的线性基为(1,2,12)。13并没有进入其中,因为它与里面的数字xor出来后得到0了。
    当我们希望13排第几大的时候,我们要知道它是与哪些数字xor后得到0的。明显知道它是与12,1这两个数字xor变成0的。于是13在所有xor出来的数字中排第5大,这些值是各不相同的
    这个与我们上次做的hdu那个求第K大的xor结果,是逆运算。
    对于1,2,12三个数字
    12 2 1
    第1小 0 0 1
    第2小 0 1 0
    第3小 0 1 1
    第4小 1 0 0
    第5小 1 0 1
    第6小 1 1 0
    然后由于线性基只有3个元素,输入的数列中有4个。所以对于没加进去的13这样的元素
    如果我们将其加入到选出来的某个子集中,它都使算出来的结果等于另子集中的另一个元素
    也就是说所有算出来的结果,都将出现2次。
    于是5*2+1=11
    还有个空集哟

    对于样例

    2

    1

    12

    12

    输出结果为3.

    对于1,12三个数字
    12 1
    第1小 0 1
    第2小 1 0
    第3小 1 1
    对于询问的12,它是与12进行xor后的。于是排名第2小,加上0,就是第3小了。

    #include<bits/stdc++.h>
    #define ll long long
    using namespace std;
    const int MAXN=31;
    const int mod=10086;
    ll n,q,ans,cnt,now,a[50];
    void insert(ll v){
        for(int i=MAXN;i>=0;--i) if((v>>i)&1){
            if(a[i]) v^=a[i];
            else{
                for(int j=i-1;j>=0;--j)
                    if((v>>j)&1) v^=a[j];
                for(int j=i+1;j<=MAXN;++j)
                    if((a[j]>>i)&1) a[j]^=v;
                a[i]=v;
                break;
            }
        }
    }
    int main(){
        scanf("%lld",&n);ll x;
        for(int i=1;i<=n;++i){
            scanf("%lld",&x);insert(x);
        }
        for(int i=0;i<=MAXN;++i) if(a[i]) cnt++;
        scanf("%lld",&q);ll tmp=cnt;
        for(int i=MAXN;i>=0;--i)
    	{
            if(a[i])
    		{
                if((q>>i)&1)
    			{
                    ans+=pow(2,tmp-1);
                }
                tmp--;
            }
        }
        for(int i=1;i<=n-cnt;++i) ans=ans*2%mod;
        printf("%lld
    ",(ans+1)%mod);
        return 0;
    }
    
  • 相关阅读:
    Single Number II
    Pascal's Triangle
    Remove Duplicates from Sorted Array
    Populating Next Right Pointers in Each Node
    Minimum Depth of Binary Tree
    Unique Paths
    Sort Colors
    Swap Nodes in Pairs
    Merge Two Sorted Lists
    Climbing Stairs
  • 原文地址:https://www.cnblogs.com/cutemush/p/12770620.html
Copyright © 2011-2022 走看看