📌  相关文章
📜  给定数组中所有对的按位或的总和

📅  最后修改于: 2021-04-21 23:49:32             🧑  作者: Mango

给定整数数组“ arr [0..n-1]”。任务是计算所有对的按位“或”的总和,即计算“ arr [i] | | |的总和” 给定数组中所有对的arr [j] ,其中i “ |”是按位OR运算符。预期时间复杂度为O(n)。

例子 :

Input:  arr[] = {5, 10, 15}
Output: 15
Required Value = (5  |  10) + (5  |  15) + (10  |  15) 
               = 15 + 15 + 15 
               = 45

Input: arr[] = {1, 2, 3, 4}
Output: 3
Required Value = (1  |  2) + (1  |  3) + (1  |  4) + 
                 (2  |  3) + (2  |  4) + (3  |  4) 
               = 3 + 3 + 5 + 3 + 6 + 7
               = 27

蛮力方法是运行两个循环,时间复杂度为O(n 2 )。

C++
// A Simple C++ program to compute sum of bitwise OR
// of all pairs
#include 
using namespace std;
  
// Returns value of "arr[0]  | arr[1] + arr[0] | arr[2] +
// ... arr[i] | arr[j] + ..... arr[n-2] |  arr[n-1]"
int pairORSum(int arr[], int n)
{
    int ans = 0; // Initialize result
  
    // Consider all pairs (arr[i], arr[j) such that
    // i < j
    for (int i = 0; i < n; i++)
        for (int j = i + 1; j < n; j++)
            ans += arr[i] | arr[j];
  
    return ans;
}
  
// Driver program to test above function
int main()
{
    int arr[] = { 1, 2, 3, 4 };
    int n = sizeof(arr) / sizeof(arr[0]);
    cout << pairORSum(arr, n) << endl;
    return 0;
}


Java
// A Simple Java program to compute
// sum of bitwise OR of all pairs
import java.io.*;
  
class GFG {
  
    // Returns value of "arr[0] | arr[1] +
    // arr[0] | arr[2] + ... arr[i] | arr[j] +
    // ..... arr[n-2] | arr[n-1]"
    static int pairORSum(int arr[], int n)
    {
        int ans = 0; // Initialize result
  
        // Consider all pairs (arr[i], arr[j)
        // such that i < j
        for (int i = 0; i < n; i++)
            for (int j = i + 1; j < n; j++)
                ans += arr[i] | arr[j];
  
        return ans;
    }
  
    // Driver program to test above function
    public static void main(String args[])
    {
        int arr[] = { 1, 2, 3, 4 };
        int n = arr.length;
        System.out.println(pairORSum(arr, n));
    }
}


Python3
# A Simple Python 3 program to compute
# sum of bitwise OR of all pairs
  
# Returns value of "arr[0] | arr[1] +
# arr[0] | arr[2] + ... arr[i] | arr[j] +
# ..... arr[n-2] | arr[n-1]"
def pairORSum(arr, n) :
    ans = 0 # Initialize result
  
    # Consider all pairs (arr[i], arr[j) 
    # such that i < j
    for i in range(0, n) :
        for j in range((i + 1), n) :
            ans = ans + arr[i] | arr[j]
  
    return ans
  
# Driver program to test above function
arr = [1, 2, 3, 4]
n = len(arr) 
print(pairORSum(arr, n))


C#
// A Simple C# program to compute
// sum of bitwise OR of all pairs
using System;
  
class GFG {
  
    // Returns value of "arr[0] | arr[1] +
    // arr[0] | arr[2] + ... arr[i] | arr[j] +
    // ..... arr[n-2] | arr[n-1]"
    static int pairORSum(int[] arr, int n)
    {
  
        int ans = 0; // Initialize result
  
        // Consider all pairs (arr[i], arr[j)
        // such that i < j
        for (int i = 0; i < n; i++)
            for (int j = i + 1; j < n; j++)
                ans += arr[i] | arr[j];
  
        return ans;
    }
  
    // Driver program to test above function
    public static void Main()
    {
        int[] arr = { 1, 2, 3, 4 };
        int n = arr.Length;
        Console.Write(pairORSum(arr, n));
    }
}


PHP


C++
// An efficient C++ program to compute sum of bitwise OR
// of all pairs
#include 
using namespace std;
typedef long long int LLI;
  
// Returns value of "arr[0] | arr[1] + arr[0] | arr[2] +
// ... arr[i] | arr[j] + ..... arr[n-2] | arr[n-1]"
  
LLI pairORSum(LLI arr[], LLI n)
{
  
    LLI ans = 0; // Initialize result
    // Traverse over all bits
    for (LLI i = 0; i < 32; i++) {
        // Count number of elements with the i'th bit set(ie., 1)
        LLI k1 = 0; // Initialize the count
  
        // Count number of elements with i’th bit not-set(ie., 0) `
        LLI k0 = 0; // Initialize the count
  
        for (LLI j = 0; j < n; j++) {
  
            if ((arr[j] & (1 << i))) // if i'th bit is set
                k1++;
            else
                k0++;
        }
        // There are k1 set bits, means k1(k1-1)/2 pairs. k1C2
        // There are k0 not-set bits and k1 set bits so total pairs will be k1*k0.
  
        // Every pair adds 2^i to the answer. Therefore,
  
        ans = ans + (1 << i) * (k1 * (k1 - 1) / 2) + (1 << i) * (k1 * k0);
    }
  
    return ans;
}
  
// Driver program to test the above function
  
int main()
  
{
  
    LLI arr[] = { 1, 2, 3, 4 };
  
    LLI n = sizeof(arr) / sizeof(arr[0]);
  
    cout << pairORSum(arr, n) << endl;
  
    return 0;
}


Java
// An efficient Java program to compute
// sum of bitwise OR of all pairs
import java.io.*;
  
class GFG {
  
    // Returns value of "arr[0] | arr[1] + arr[0] | arr[2] +
    // ... arr[i] | arr[j] + ..... arr[n-2] | arr[n-1]"
    static int pairORSum(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 the ith bit set(ie., 1)
            int k1 = 0; // Initialize the count
  
            // Count number of elements with ith bit not-set(ie., 0) `
            int k0 = 0; // Initialize the count
  
            for (int j = 0; j < n; j++) {
  
                if ((arr[j] & (1 << i)) != 0) // if i'th bit is set
                    k1++;
                else
                    k0++;
            }
            // There are k1 set bits, means k1(k1-1)/2 pairs. k1C2
            // There are k0 not-set bits and k1 set bits so total pairs will be k1*k0.
            // Every pair adds 2^i to the answer. Therefore,
  
            ans = ans + (1 << i) * (k1 * (k1 - 1) / 2) + (1 << i) * (k1 * k0);
        }
  
        return ans;
    }
  
    // Driver program to test above function
    public static void main(String args[])
    {
        int arr[] = { 1, 2, 3, 4 };
        int n = arr.length;
        System.out.println(pairORSum(arr, n));
    }
}


Python3
# An efficient Python 3 program to
# compute the sum of bitwise OR of all pairs
  
# Returns value of "arr[0] | arr[1] + arr[0] | arr[2] +
# ... arr[i] | arr[j] + ..... arr[n-2] | arr[n-1]"
  
def pairORSum(arr, n) :
    # Initialize result
    ans = 0
    # Traverse over all bits
    for i in range(0, 32) :
        # Count number of elements with the i'th bit set(ie., 1)
        k1 = 0
          
        # Count number of elements with i’th bit not-set(ie., 0) `
        k0 = 0
          
        for j in range(0, n) :
              
            if( (arr[j] & (1<


C#
// An efficient C# program to compute
// sum of bitwise OR of all pairs
using System;
  
class GFG {
  
    // Returns value of "arr[0] | arr[1] + arr[0] | arr[2] +
    // ... arr[i] | arr[j] + ..... arr[n-2] | arr[n-1]"
    static int pairORSum(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 the ith bit set(ie., 1)
            int k1 = 0; // Initialize the count
  
            // Count number of elements with ith bit not-set(ie., 0) `
            int k0 = 0; // Initialize the count
  
            for (int j = 0; j < n; j++) {
                // if i'th bit is set
                if ((arr[j] & (1 << i)) != 0)
                    k1++;
                else
                    k0++;
            }
            // There are k1 set bits, means k1(k1-1)/2 pairs. k1C2
            // There are k0 not-set bits and k1 set bits so total pairs will be k1*k0.
            // Every pair adds 2^i to the answer. Therefore,
  
            ans = ans + (1 << i) * (k1 * (k1 - 1) / 2) + (1 << i) * (k1 * k0);
        }
  
        return ans;
    }
  
    // Driver program to test above function
    public static void Main()
    {
        int[] arr = new int[] { 1, 2, 3, 4 };
        int n = arr.Length;
  
        Console.Write(pairORSum(arr, n));
    }
}


PHP


输出 :

27

一个有效的解决方案可以在O(n)时间内解决此问题。这里的假设是整数使用32位表示。

这个想法是要对每个第i个位置(i> = 0 && i <= 31)的设置位数进行计数。如果两个数字中的对应位等于1,则两个数字的AND的第i位为1。

k1为第i个位置的设置位数。第i个置位的对的总数为k1 C 2 = k1 *(k1-1)/ 2(计数k1表示有第i个置位的k1个数字)。每对这样的总和就加2 i 。同样,共有k0个值,在第i个位置没有设置位。现在,每个元素(尚未在第i个位置设置位的元素)都可以与k1个元素(即那些在第i个位置设置了位的元素)配对,因此共有k1 * k0对,每对这样的货币对也将2 i加到总和上。

总和=总和+(1 << i)*(k1 *(k1-1)/ 2)+(1 << i)*(k1 * k0)

这个想法类似于找到所有对之间的位差之和。

下面是上述方法的实现:

C++

// An efficient C++ program to compute sum of bitwise OR
// of all pairs
#include 
using namespace std;
typedef long long int LLI;
  
// Returns value of "arr[0] | arr[1] + arr[0] | arr[2] +
// ... arr[i] | arr[j] + ..... arr[n-2] | arr[n-1]"
  
LLI pairORSum(LLI arr[], LLI n)
{
  
    LLI ans = 0; // Initialize result
    // Traverse over all bits
    for (LLI i = 0; i < 32; i++) {
        // Count number of elements with the i'th bit set(ie., 1)
        LLI k1 = 0; // Initialize the count
  
        // Count number of elements with i’th bit not-set(ie., 0) `
        LLI k0 = 0; // Initialize the count
  
        for (LLI j = 0; j < n; j++) {
  
            if ((arr[j] & (1 << i))) // if i'th bit is set
                k1++;
            else
                k0++;
        }
        // There are k1 set bits, means k1(k1-1)/2 pairs. k1C2
        // There are k0 not-set bits and k1 set bits so total pairs will be k1*k0.
  
        // Every pair adds 2^i to the answer. Therefore,
  
        ans = ans + (1 << i) * (k1 * (k1 - 1) / 2) + (1 << i) * (k1 * k0);
    }
  
    return ans;
}
  
// Driver program to test the above function
  
int main()
  
{
  
    LLI arr[] = { 1, 2, 3, 4 };
  
    LLI n = sizeof(arr) / sizeof(arr[0]);
  
    cout << pairORSum(arr, n) << endl;
  
    return 0;
}

Java

// An efficient Java program to compute
// sum of bitwise OR of all pairs
import java.io.*;
  
class GFG {
  
    // Returns value of "arr[0] | arr[1] + arr[0] | arr[2] +
    // ... arr[i] | arr[j] + ..... arr[n-2] | arr[n-1]"
    static int pairORSum(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 the ith bit set(ie., 1)
            int k1 = 0; // Initialize the count
  
            // Count number of elements with ith bit not-set(ie., 0) `
            int k0 = 0; // Initialize the count
  
            for (int j = 0; j < n; j++) {
  
                if ((arr[j] & (1 << i)) != 0) // if i'th bit is set
                    k1++;
                else
                    k0++;
            }
            // There are k1 set bits, means k1(k1-1)/2 pairs. k1C2
            // There are k0 not-set bits and k1 set bits so total pairs will be k1*k0.
            // Every pair adds 2^i to the answer. Therefore,
  
            ans = ans + (1 << i) * (k1 * (k1 - 1) / 2) + (1 << i) * (k1 * k0);
        }
  
        return ans;
    }
  
    // Driver program to test above function
    public static void main(String args[])
    {
        int arr[] = { 1, 2, 3, 4 };
        int n = arr.length;
        System.out.println(pairORSum(arr, n));
    }
}

Python3

# An efficient Python 3 program to
# compute the sum of bitwise OR of all pairs
  
# Returns value of "arr[0] | arr[1] + arr[0] | arr[2] +
# ... arr[i] | arr[j] + ..... arr[n-2] | arr[n-1]"
  
def pairORSum(arr, n) :
    # Initialize result
    ans = 0
    # Traverse over all bits
    for i in range(0, 32) :
        # Count number of elements with the i'th bit set(ie., 1)
        k1 = 0
          
        # Count number of elements with i’th bit not-set(ie., 0) `
        k0 = 0
          
        for j in range(0, n) :
              
            if( (arr[j] & (1<

C#

// An efficient C# program to compute
// sum of bitwise OR of all pairs
using System;
  
class GFG {
  
    // Returns value of "arr[0] | arr[1] + arr[0] | arr[2] +
    // ... arr[i] | arr[j] + ..... arr[n-2] | arr[n-1]"
    static int pairORSum(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 the ith bit set(ie., 1)
            int k1 = 0; // Initialize the count
  
            // Count number of elements with ith bit not-set(ie., 0) `
            int k0 = 0; // Initialize the count
  
            for (int j = 0; j < n; j++) {
                // if i'th bit is set
                if ((arr[j] & (1 << i)) != 0)
                    k1++;
                else
                    k0++;
            }
            // There are k1 set bits, means k1(k1-1)/2 pairs. k1C2
            // There are k0 not-set bits and k1 set bits so total pairs will be k1*k0.
            // Every pair adds 2^i to the answer. Therefore,
  
            ans = ans + (1 << i) * (k1 * (k1 - 1) / 2) + (1 << i) * (k1 * k0);
        }
  
        return ans;
    }
  
    // Driver program to test above function
    public static void Main()
    {
        int[] arr = new int[] { 1, 2, 3, 4 };
        int n = arr.Length;
  
        Console.Write(pairORSum(arr, n));
    }
}

的PHP


输出

27