📜  所有对之间的位差总和

📅  最后修改于: 2021-04-26 18:39:13             🧑  作者: Mango

给定一个n个整数的整数数组,找到可以由数组元素形成的所有对中的位差之和。一对(x,y)的位差是x和y的二进制表示形式中相同位置上不同位的计数。
例如,2和7的位差为2。2的二进制表示形式为010,7的二进制表示形式为111(第一位和最后一位的数字不同)。

例子 :

Input: arr[] = {1, 2}
Output: 4
All pairs in array are (1, 1), (1, 2)
                       (2, 1), (2, 2)
Sum of bit differences = 0 + 2 +
                         2 + 0
                      = 4

Input:  arr[] = {1, 3, 5}
Output: 8
All pairs in array are (1, 1), (1, 3), (1, 5)
                       (3, 1), (3, 3) (3, 5),
                       (5, 1), (5, 3), (5, 5)
Sum of bit differences =  0 + 1 + 1 +
                          1 + 0 + 2 +
                          1 + 2 + 0 
                       = 8

资料来源:Google面试问题

天真的解决方案–
一个简单的解决方案是运行两个循环,一个接一个地考虑所有对。对于每对,计算位差异。最后返回计数总和。该解决方案的时间复杂度为O(n 2 )。我们正在使用bitset :: count() 这是C++中的内置STL,它以数字的二进制表示形式返回设置的位数。

C++
// C++ program to compute sum of pairwise bit differences
#include 
using namespace std;
 
int sum_bit_diff(vector a)
{
    int n = a.size();
    int ans = 0;
 
    for (int i = 0; i < n - 1; i++) {
        int count = 0;
 
        for (int j = i; j < n; j++) {
            // Bitwise and of pair (a[i], a[j])
            int x = a[i] & a[j];
            // Bitwise or of pair (a[i], a[j])
            int y = a[i] | a[j];
 
            bitset<32> b1(x);
            bitset<32> b2(y);
 
            // to count set bits in and of two numbers
            int r1 = b1.count();
            // to count set bits in or of two numbers
            int r2 = b2.count();
 
            // Absolute differences at individual bit positions of two
            // numbers is contributed by pair (a[i], a[j]) in count
            count = abs(r1 - r2);
 
            // each pair adds twice of contributed count
            // as both (a, b) and (b, a) are considered
            // two separate pairs.
            ans = ans + (2 * count);
        }
    }
    return ans;
}
 
int main()
{
 
    vector nums{ 10, 5 };
    int ans = sum_bit_diff(nums);
 
    cout << ans;
}


C++
// C++ program to compute sum of pairwise bit differences
#include 
using namespace std;
 
int sumBitDifferences(int arr[], int n)
{
    int ans = 0; // Initialize result
 
    // traverse over all bits
    for (int i = 0; i < 32; i++) {
        // count number of elements with i'th bit set
        int count = 0;
        for (int j = 0; j < n; j++)
            if ((arr[j] & (1 << i)))
                count++;
 
        // Add "count * (n - count) * 2" to the answer
        ans += (count * (n - count) * 2);
    }
 
    return ans;
}
 
// Driver prorgram
int main()
{
    int arr[] = { 1, 3, 5 };
    int n = sizeof arr / sizeof arr[0];
    cout << sumBitDifferences(arr, n) << endl;
    return 0;
}


Java
// Java program to compute sum of pairwise
// bit differences
 
import java.io.*;
 
class GFG {
 
    static int sumBitDifferences(int arr[], int n)
    {
 
        int ans = 0; // Initialize result
 
        // traverse over all bits
        for (int i = 0; i < 32; i++) {
 
            // count number of elements
            // with i'th bit set
            int count = 0;
 
            for (int j = 0; j < n; j++)
                if ((arr[j] & (1 << i)) == 0)
                    count++;
 
            // Add "count * (n - count) * 2"
            // to the answer
            ans += (count * (n - count) * 2);
        }
 
        return ans;
    }
 
    // Driver prorgram
    public static void main(String args[])
    {
 
        int arr[] = { 1, 3, 5 };
        int n = arr.length;
 
        System.out.println(sumBitDifferences(
            arr, n));
    }
}
 
// This code is contributed by Anshika Goyal.


Python3
# Python program to compute sum of pairwise bit differences
 
def sumBitDifferences(arr, n):
 
    ans = 0  # Initialize result
 
    # traverse over all bits
    for i in range(0, 32):
     
        # count number of elements with i'th bit set
        count = 0
        for j in range(0, n):
            if ( (arr[j] & (1 << i)) ):
                count+= 1
 
        # Add "count * (n - count) * 2" to the answer
        ans += (count * (n - count) * 2);
     
    return ans
 
# Driver prorgram
arr = [1, 3, 5]
n = len(arr )
print(sumBitDifferences(arr, n))
 
# This code is contributed by
# Smitha Dinesh Semwal


C#
// C# program to compute sum
// of pairwise bit differences
using System;
 
class GFG {
    static int sumBitDifferences(int[] arr,
                                 int n)
    {
        int ans = 0; // Initialize result
 
        // traverse over all bits
        for (int i = 0; i < 32; i++) {
 
            // count number of elements
            // with i'th bit set
            int count = 0;
            for (int j = 0; j < n; j++)
                if ((arr[j] & (1 << i)) == 0)
                    count++;
 
            // Add "count * (n - count) * 2"
            // to the answer
            ans += (count * (n - count) * 2);
        }
 
        return ans;
    }
    // Driver Code
    public static void Main()
    {
 
        int[] arr = { 1, 3, 5 };
        int n = arr.Length;
 
        Console.Write(sumBitDifferences(arr, n));
    }
}
 
// This code is contributed by ajit


PHP


Javascript


高效的解决方案–

一个有效的解决方案可以利用O(n)时间解决此问题,因为所有数字都使用32位(或某些固定位数)表示。这个想法是要计算各个位位置的差异。我们从0遍历到31,并在第i个位置1计数数字。让此计数为“计数”。将会有未设置第i位的“ n个计数”数字。因此,第i个位的差异计数为“ count *(n-count)* 2”,该公式的原因是因为每对都具有一个在第i个位置设置了位的元素,而第二个元素具有未设置的位在第i个位置,正好对总和贡献1,因此总置换计数将为count *(n-count),并乘以2是由于按照使对1 <= i,j≤N。

以下是上述想法的实现。

C++

// C++ program to compute sum of pairwise bit differences
#include 
using namespace std;
 
int sumBitDifferences(int arr[], int n)
{
    int ans = 0; // Initialize result
 
    // traverse over all bits
    for (int i = 0; i < 32; i++) {
        // count number of elements with i'th bit set
        int count = 0;
        for (int j = 0; j < n; j++)
            if ((arr[j] & (1 << i)))
                count++;
 
        // Add "count * (n - count) * 2" to the answer
        ans += (count * (n - count) * 2);
    }
 
    return ans;
}
 
// Driver prorgram
int main()
{
    int arr[] = { 1, 3, 5 };
    int n = sizeof arr / sizeof arr[0];
    cout << sumBitDifferences(arr, n) << endl;
    return 0;
}

Java

// Java program to compute sum of pairwise
// bit differences
 
import java.io.*;
 
class GFG {
 
    static int sumBitDifferences(int arr[], int n)
    {
 
        int ans = 0; // Initialize result
 
        // traverse over all bits
        for (int i = 0; i < 32; i++) {
 
            // count number of elements
            // with i'th bit set
            int count = 0;
 
            for (int j = 0; j < n; j++)
                if ((arr[j] & (1 << i)) == 0)
                    count++;
 
            // Add "count * (n - count) * 2"
            // to the answer
            ans += (count * (n - count) * 2);
        }
 
        return ans;
    }
 
    // Driver prorgram
    public static void main(String args[])
    {
 
        int arr[] = { 1, 3, 5 };
        int n = arr.length;
 
        System.out.println(sumBitDifferences(
            arr, n));
    }
}
 
// This code is contributed by Anshika Goyal.

Python3

# Python program to compute sum of pairwise bit differences
 
def sumBitDifferences(arr, n):
 
    ans = 0  # Initialize result
 
    # traverse over all bits
    for i in range(0, 32):
     
        # count number of elements with i'th bit set
        count = 0
        for j in range(0, n):
            if ( (arr[j] & (1 << i)) ):
                count+= 1
 
        # Add "count * (n - count) * 2" to the answer
        ans += (count * (n - count) * 2);
     
    return ans
 
# Driver prorgram
arr = [1, 3, 5]
n = len(arr )
print(sumBitDifferences(arr, n))
 
# This code is contributed by
# Smitha Dinesh Semwal   

C#

// C# program to compute sum
// of pairwise bit differences
using System;
 
class GFG {
    static int sumBitDifferences(int[] arr,
                                 int n)
    {
        int ans = 0; // Initialize result
 
        // traverse over all bits
        for (int i = 0; i < 32; i++) {
 
            // count number of elements
            // with i'th bit set
            int count = 0;
            for (int j = 0; j < n; j++)
                if ((arr[j] & (1 << i)) == 0)
                    count++;
 
            // Add "count * (n - count) * 2"
            // to the answer
            ans += (count * (n - count) * 2);
        }
 
        return ans;
    }
    // Driver Code
    public static void Main()
    {
 
        int[] arr = { 1, 3, 5 };
        int n = arr.Length;
 
        Console.Write(sumBitDifferences(arr, n));
    }
}
 
// This code is contributed by ajit

的PHP


Java脚本


输出 :

8
 
询问:Google