zoukankan      html  css  js  c++  java
  • 福建工程学院第十四届ACM校赛B题题解

    第二集,未来的我发量这么捉急的吗

    题意:

    有n个数,请问有多少对数字(i,j)(1<=i<j<=n),满足(a[i]^a[j])+((a[i]&a[j])<<1)=k

    思路:

    仔细观察不难发现这个位运算有点不一般,其实(a[i]^a[j])+((a[i]&a[j])<<1)这个是等价于a[i]+a[j]的,具体的原理是这样的,我们模拟一下二进制下的加法,如果这一位都是0,加完之后还是0,如果这一位是一个0和一个1,加完之后变成了1,如果这一位都是1,加完之后又就变成了0,然后向前进位,可以观察到在不考虑进位的情况下,二进制加法和异或的性质是一样的,0+0=0,0+1=1+0=1,1+1=0,然后我们发现a[i]&a[j]其实是把二进制都为1的位置提取了出来,因为两个数都为1的情况是需要进位的,所以这里模拟二进制加法,多了个(a[i]&a[j])<<1这样的进位量。

    代码实现

    这题代码挺简单,排序双指针或者标记都行,map标记代码如下:

    #include <iostream>
    
    #include <cstring>
    
    #include <map>
    
    using namespace std;
    
    typedef long long ll;
    
    typedef unsigned long long ull;
    
    const int maxn = 1e5+7;
    
    int a[maxn];
    
    int main(){
    
        ios::sync_with_stdio(false);
    
        cin.tie(0);
    
        int T;
    
        cin>>T;
    
        while(T--){
    
            map<int,int> mp;
    
            int n,k;
    
            cin>>n>>k;
    
            ll ans=0;
    
            for(int i=1;i<=n;i++){
    
                cin>>a[i];
    
                ans+=mp[k-a[i]];
    
                mp[a[i]]++;
    
            }
    
            cout<<ans<<endl;
    
        }
    
        return 0;
    
    }
  • 相关阅读:
    URL的JavaScript解决之道
    JavaScript中Date对象的几个扩展方法
    taobao open
    Linux操作系统的日志说明
    DG常用运维命令及常见问题解决
    oracle系统视图
    oracle 自动备份、恢复功能
    oracle队列
    spring学习笔记
    sql语句拾遗
  • 原文地址:https://www.cnblogs.com/xseventh/p/10878237.html
Copyright © 2011-2022 走看看