• CodeForces 734F Anton and School


    位运算。

    两个数的和:$A+B=(AandB)+(AorB)$,那么$b[i]+c[i]=n*a[i]+suma$。可以解出一组解,然后再按位统计贡献验证一下。

    #pragma comment(linker, "/STACK:1024000000,1024000000")
    #include<cstdio>
    #include<cstring>
    #include<cmath>
    #include<algorithm>
    #include<vector>
    #include<map>
    #include<set>
    #include<queue>
    #include<stack>
    #include<ctime>
    #include<iostream>
    using namespace std;
    typedef long long LL;
    const double pi=acos(-1.0);
    void File()
    {
        freopen("D:\in.txt","r",stdin);
        freopen("D:\out.txt","w",stdout);
    }
    template <class T>
    inline void read(T &x)
    {
        char c = getchar();
        x = 0;
        while(!isdigit(c)) c = getchar();
        while(isdigit(c))
        {
            x = x * 10 + c - '0';
            c = getchar();
        }
    }
    
    LL sum,sumc,sumb;
    LL t[70],g[70],a[200010],b[200010],c[200010];
    int n;
    
    int main()
    {
        g[0]=1; for(int i=1;i<=62;i++) g[i]=g[i-1]*2;
        cin>>n;
        for(int i=1;i<=n;i++)
        {
            cin>>b[i];
            sumb=sumb+b[i];
        }
    
        for(int i=1;i<=n;i++)
        {
            cin>>c[i];
            sumc=sumc+c[i];
        }
    
        if((sumb+sumc)%(LL)(2*n)!=0)
        {
            printf("-1
    ");
            return 0;
        }
    
        sum=(sumb+sumc)/(LL)(2*n);
    
        for(int i=1;i<=n;i++)
        {
            if((b[i]+c[i]-sum)<0)
            {
                printf("-1
    ");
                return 0;
            }
    
            if((b[i]+c[i]-sum)%(LL)n!=0)
            {
                printf("-1
    ");
                return 0;
            }
    
            a[i]=(b[i]+c[i]-sum)/(LL)n;
        }
    
        for(int i=1;i<=n;i++)
            for(int j=0;j<=62;j++) if(a[i]&g[j]) t[j]++;
    
        bool fail=0;
    
        for(int i=1;i<=n;i++)
        {
            long long sum=0;
            for(int j=0;j<=62;j++) if(a[i]&g[j]) sum=sum+t[j]*g[j];
            if(sum!=b[i]) fail=1;
    
            sum=0;
            for(int j=0;j<=62;j++)
            {
                if(a[i]&g[j]) sum=sum+n*g[j];
                else sum=sum+t[j]*g[j];
            }
            if(sum!=c[i]) fail=1;
        }
    
        if(fail==0)
        {
            for(int i=1;i<=n;i++) cout<<a[i]<<" ";
            cout<<endl;
        }
        else cout<<"-1"<<endl;
    
        return 0;
    }
  • 相关阅读:
    C#遍历访问Dictionary和HashTable
    SQL:select case when(转)
    微软四大名著
    中国 Erlounge III 归来,好消息一箩筐!
    原来,程序的世界远比我想象的精彩
    Google和Yahoo专家联手揭秘世界顶尖公司的技术内幕
    有意义,不容易!(一位译者的翻译感言)
    世界级Oracle专家权威力作
    国内第一部DWR著作
    SQL Server故障排除圣经
  • 原文地址:https://www.cnblogs.com/zufezzt/p/6391190.html
Copyright © 2020-2023  润新知