Sum of XOR of all subarrays
The problem at hand is to calculate the sum of XOR of all subarrays of a given array. In simpler terms, given an array of integers, we want to find the XOR of all possible subarrays and then sum up those XOR values.
Problem Statement
Given an array of integers, the task is to find the sum of the XOR values of all subarrays that can be formed from the given array.
Description
To better understand the problem, let's take an example. Consider the array: [7, 2, 5, 1]
.
- Subarrays of length 1:
[7], [2], [5], [1]
. XOR of each subarray is[7], [2], [5], [1]
respectively. - Subarrays of length 2:
[7, 2], [2, 5], [5, 1]
. XOR of each subarray is[5], [7], [4]
respectively. - Subarrays of length 3:
[7, 2, 5], [2, 5, 1]
. XOR of each subarray is[0], [6]
respectively. - Subarray of length 4:
[7, 2, 5, 1]
. XOR of the subarray is[5]
.
Now, if we sum up all these XOR values: 7 + 2 + 5 + 1 + 5 + 7 + 4 + 0 + 6 + 5 = 38
. This is the desired
result.
Idea to Solve
To efficiently solve this problem, we can observe that the XOR operation is bitwise in nature. We can focus on the individual bits of the array elements and count the occurrences of 1s in those bits. Based on this observation, we can formulate an algorithm to calculate the sum of XOR values for all subarrays.
Algorithm
-
Initialize variables
sum
to store the final result,multiplier
to keep track of the power of 2,oddBits
to count the odd occurrences of 1s, andisOdd
to indicate whether the oddBits count is currently odd or even. -
Loop through each bit position from 0 to 29 (assuming the array elements are 32-bit integers): a. Initialize
oddBits
to 0 andisOdd
to false. b. Loop through each element in the array: i. If the current bit at the bit position is 1, toggle theisOdd
flag. ii. IfisOdd
is true, incrementoddBits
. c. Loop through each element in the array: i. Update thesum
by addingmultiplier * oddBits
. ii. If the current bit at the bit position is 1, updateoddBits
to(n - j - oddBits)
. -
After both inner loops finish, reset
isOdd
to false andoddBits
to 0. -
Multiply
multiplier
by 2. -
Repeat steps 2-4 for all bit positions.
-
Print the final value of
sum
.
Pseudocode
sumSubarrayXor(arr[], n):
sum = 0
multiplier = 1
oddBits = 0
isOdd = false
for i = 0 to 29:
oddBits = 0
isOdd = false
for j = 0 to n - 1:
if (arr[j] & (1 << i)) != 0:
isOdd = !isOdd
if isOdd:
oddBits++
for j = 0 to n - 1:
sum = sum + (multiplier * oddBits)
if (arr[j] & (1 << i)) != 0:
oddBits = n - j - oddBits
isOdd = false
oddBits = 0
multiplier = multiplier * 2
print("XOR Sum:", sum)
Code Solution
// C Program
// Sum of XOR of all subarrays
#include <stdio.h>
#include <stdbool.h>
void sumSubarrayXor(int arr[], int n)
{
// Define some auxiliary variables
int sum = 0;
int multiplier = 1;
int oddBits = 0;
bool isOdd = false;
// Working on initial 30 bits
for (int i = 0; i < 30; i++)
{
// Count active bits in alternate elements
for (int j = 0; j < n; j++)
{
// Check (1 << i) bit is active or not
if ((arr[j] & (1 << i)) != 0)
{
// Change the status
isOdd = !isOdd;
}
if (isOdd == true)
{
// Increase counter position
oddBits++;
}
}
for (int j = 0; j < n; j++)
{
// Change resultant sum
sum = sum + (multiplier * oddBits);
if ((arr[j] & (1 << i)) != 0)
{
oddBits = (n - j - oddBits);
}
}
// Reset odd counter indicator
isOdd = false;
oddBits = 0;
// Increase the multiplier by twice
multiplier = multiplier * 2;
}
// Display calculated result
printf("XOR Sum : %d", sum);
}
int main()
{
int arr[] = {
7 , 2 , 5 , 1
};
// Get the size of arr
int n = sizeof(arr) / sizeof(arr[0]);
/*
(7) + (2) + (5) + (1) +
(7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
(7^ 2^ 5) + (2^ 5 ^ 1) +
(7^ 2^ 5^ 1)
--------------
38
--------------
*/
sumSubarrayXor(arr, n);
return 0;
}
input
XOR Sum : 38
/*
Java Program for
Sum of XOR of all subarrays
*/
public class Subarray
{
public void sumSubarrayXor(int[] arr, int n)
{
// Define some auxiliary variables
int sum = 0;
int multiplier = 1;
int oddBits = 0;
boolean isOdd = false;
// Working on initial 30 bits
for (int i = 0; i < 30; i++)
{
// Count active bits in alternate elements
for (int j = 0; j < n; j++)
{
// Check (1 << i) bit is active or not
if ((arr[j] & (1 << i)) != 0)
{
// Change the status
isOdd = !isOdd;
}
if (isOdd == true)
{
// Increase counter position
oddBits++;
}
}
for (int j = 0; j < n; j++)
{
// Change resultant sum
sum = sum + (multiplier * oddBits);
if ((arr[j] & (1 << i)) != 0)
{
oddBits = (n - j - oddBits);
}
}
// Reset odd counter indicator
isOdd = false;
oddBits = 0;
// Increase the multiplier by twice
multiplier = multiplier * 2;
}
// Display calculated result
System.out.print("XOR Sum : " + sum);
}
public static void main(String[] args)
{
Subarray task = new Subarray();
int[] arr = {
7 , 2 , 5 , 1
};
// Get the size of arr
int n = arr.length;
/*
(7) + (2) + (5) + (1) +
(7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
(7^ 2^ 5) + (2^ 5 ^ 1) +
(7^ 2^ 5^ 1)
--------------
38
--------------
*/
task.sumSubarrayXor(arr, n);
}
}
input
XOR Sum : 38
// Include header file
#include <iostream>
using namespace std;
/*
C++ Program for
Sum of XOR of all subarrays
*/
class Subarray
{
public: void sumSubarrayXor(int arr[], int n)
{
// Define some auxiliary variables
int sum = 0;
int multiplier = 1;
int oddBits = 0;
bool isOdd = false;
// Working on initial 30 bits
for (int i = 0; i < 30; i++)
{
// Count active bits in alternate elements
for (int j = 0; j < n; j++)
{
// Check (1 << i) bit is active or not
if ((arr[j] &(1 << i)) != 0)
{
// Change the status
isOdd = !isOdd;
}
if (isOdd == true)
{
// Increase counter position
oddBits++;
}
}
for (int j = 0; j < n; j++)
{
// Change resultant sum
sum = sum + (multiplier *oddBits);
if ((arr[j] &(1 << i)) != 0)
{
oddBits = (n - j - oddBits);
}
}
// Reset odd counter indicator
isOdd = false;
oddBits = 0;
// Increase the multiplier by twice
multiplier = multiplier *2;
}
// Display calculated result
cout << "XOR Sum : " << sum;
}
};
int main()
{
Subarray *task = new Subarray();
int arr[] = {7 , 2 , 5 , 1};
// Get the size of arr
int n = sizeof(arr) / sizeof(arr[0]);
/*
(7) + (2) + (5) + (1) +
(7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
(7^ 2^ 5) + (2^ 5 ^ 1) +
(7^ 2^ 5^ 1)
--------------
38
--------------
*/
task->sumSubarrayXor(arr, n);
return 0;
}
input
XOR Sum : 38
// Include namespace system
using System;
/*
Csharp Program for
Sum of XOR of all subarrays
*/
public class Subarray
{
public void sumSubarrayXor(int[] arr, int n)
{
// Define some auxiliary variables
int sum = 0;
int multiplier = 1;
int oddBits = 0;
Boolean isOdd = false;
// Working on initial 30 bits
for (int i = 0; i < 30; i++)
{
// Count active bits in alternate elements
for (int j = 0; j < n; j++)
{
// Check (1 << i) bit is active or not
if ((arr[j] & (1 << i)) != 0)
{
// Change the status
isOdd = !isOdd;
}
if (isOdd == true)
{
// Increase counter position
oddBits++;
}
}
for (int j = 0; j < n; j++)
{
// Change resultant sum
sum = sum + (multiplier * oddBits);
if ((arr[j] & (1 << i)) != 0)
{
oddBits = (n - j - oddBits);
}
}
// Reset odd counter indicator
isOdd = false;
oddBits = 0;
// Increase the multiplier by twice
multiplier = multiplier * 2;
}
// Display calculated result
Console.Write("XOR Sum : " + sum);
}
public static void Main(String[] args)
{
Subarray task = new Subarray();
int[] arr = {
7 , 2 , 5 , 1
};
// Get the size of arr
int n = arr.Length;
/*
(7) + (2) + (5) + (1) +
(7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
(7^ 2^ 5) + (2^ 5 ^ 1) +
(7^ 2^ 5^ 1)
--------------
38
--------------
*/
task.sumSubarrayXor(arr, n);
}
}
input
XOR Sum : 38
<?php
/*
Php Program for
Sum of XOR of all subarrays
*/
class Subarray
{
public function sumSubarrayXor($arr, $n)
{
// Define some auxiliary variables
$sum = 0;
$multiplier = 1;
$oddBits = 0;
$isOdd = false;
// Working on initial 30 bits
for ($i = 0; $i < 30; $i++)
{
// Count active bits in alternate elements
for ($j = 0; $j < $n; $j++)
{
// Check (1 << i) bit is active or not
if (($arr[$j] & (1 << $i)) != 0)
{
// Change the status
$isOdd = !$isOdd;
}
if ($isOdd == true)
{
// Increase counter position
$oddBits++;
}
}
for ($j = 0; $j < $n; $j++)
{
// Change resultant sum
$sum = $sum + ($multiplier * $oddBits);
if (($arr[$j] & (1 << $i)) != 0)
{
$oddBits = ($n - $j - $oddBits);
}
}
// Reset odd counter indicator
$isOdd = false;
$oddBits = 0;
// Increase the multiplier by twice
$multiplier = $multiplier * 2;
}
// Display calculated result
echo("XOR Sum : ".$sum);
}
}
function main()
{
$task = new Subarray();
$arr = array(7, 2, 5, 1);
// Get the size of arr
$n = count($arr);
/*
(7) + (2) + (5) + (1) +
(7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
(7^ 2^ 5) + (2^ 5 ^ 1) +
(7^ 2^ 5^ 1)
--------------
38
--------------
*/
$task->sumSubarrayXor($arr, $n);
}
main();
input
XOR Sum : 38
/*
Node JS Program for
Sum of XOR of all subarrays
*/
class Subarray
{
sumSubarrayXor(arr, n)
{
// Define some auxiliary variables
var sum = 0;
var multiplier = 1;
var oddBits = 0;
var isOdd = false;
// Working on initial 30 bits
for (var i = 0; i < 30; i++)
{
// Count active bits in alternate elements
for (var j = 0; j < n; j++)
{
// Check (1 << i) bit is active or not
if ((arr[j] & (1 << i)) != 0)
{
// Change the status
isOdd = !isOdd;
}
if (isOdd == true)
{
// Increase counter position
oddBits++;
}
}
for (var j = 0; j < n; j++)
{
// Change resultant sum
sum = sum + (multiplier * oddBits);
if ((arr[j] & (1 << i)) != 0)
{
oddBits = (n - j - oddBits);
}
}
// Reset odd counter indicator
isOdd = false;
oddBits = 0;
// Increase the multiplier by twice
multiplier = multiplier * 2;
}
// Display calculated result
process.stdout.write("XOR Sum : " + sum);
}
}
function main()
{
var task = new Subarray();
var arr = [7, 2, 5, 1];
// Get the size of arr
var n = arr.length;
/*
(7) + (2) + (5) + (1) +
(7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
(7^ 2^ 5) + (2^ 5 ^ 1) +
(7^ 2^ 5^ 1)
--------------
38
--------------
*/
task.sumSubarrayXor(arr, n);
}
main();
input
XOR Sum : 38
# Python 3 Program for
# Sum of XOR of all subarrays
class Subarray :
def sumSubarrayXor(self, arr, n) :
# Define some auxiliary variables
sum = 0
multiplier = 1
oddBits = 0
isOdd = False
i = 0
# Working on initial 30 bits
while (i < 30) :
j = 0
# Count active bits in alternate elements
while (j < n) :
# Check (1 << i) bit is active or not
if ((arr[j] & (1 << i)) != 0) :
# Change the status
isOdd = not isOdd
if (isOdd == True) :
# Increase counter position
oddBits += 1
j += 1
j = 0
while (j < n) :
# Change resultant sum
sum = sum + (multiplier * oddBits)
if ((arr[j] & (1 << i)) != 0) :
oddBits = (n - j - oddBits)
j += 1
# Reset odd counter indicator
isOdd = False
oddBits = 0
# Increase the multiplier by twice
multiplier = multiplier * 2
i += 1
# Display calculated result
print("XOR Sum : ", sum, end = "")
def main() :
task = Subarray()
arr = [7, 2, 5, 1]
# Get the size of arr
n = len(arr)
# (7) + (2) + (5) + (1) +
# (7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
# (7^ 2^ 5) + (2^ 5 ^ 1) +
# (7^ 2^ 5^ 1)
# --------------
# 38
# --------------
task.sumSubarrayXor(arr, n)
if __name__ == "__main__": main()
input
XOR Sum : 38
# Ruby Program for
# Sum of XOR of all subarrays
class Subarray
def sumSubarrayXor(arr, n)
# Define some auxiliary variables
sum = 0
multiplier = 1
oddBits = 0
isOdd = false
i = 0
# Working on initial 30 bits
while (i < 30)
j = 0
# Count active bits in alternate elements
while (j < n)
# Check (1 << i) bit is active or not
if ((arr[j] & (1 << i)) != 0)
# Change the status
isOdd = !isOdd
end
if (isOdd == true)
# Increase counter position
oddBits += 1
end
j += 1
end
j = 0
while (j < n)
# Change resultant sum
sum = sum + (multiplier * oddBits)
if ((arr[j] & (1 << i)) != 0)
oddBits = (n - j - oddBits)
end
j += 1
end
# Reset odd counter indicator
isOdd = false
oddBits = 0
# Increase the multiplier by twice
multiplier = multiplier * 2
i += 1
end
# Display calculated result
print("XOR Sum : ", sum)
end
end
def main()
task = Subarray.new()
arr = [7, 2, 5, 1]
# Get the size of arr
n = arr.length
# (7) + (2) + (5) + (1) +
# (7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
# (7^ 2^ 5) + (2^ 5 ^ 1) +
# (7^ 2^ 5^ 1)
# --------------
# 38
# --------------
task.sumSubarrayXor(arr, n)
end
main()
input
XOR Sum : 38
/*
Scala Program for
Sum of XOR of all subarrays
*/
class Subarray()
{
def sumSubarrayXor(arr: Array[Int], n: Int): Unit = {
// Define some auxiliary variables
var sum: Int = 0;
var multiplier: Int = 1;
var oddBits: Int = 0;
var isOdd: Boolean = false;
var i: Int = 0;
// Working on initial 30 bits
while (i < 30)
{
var j: Int = 0;
// Count active bits in alternate elements
while (j < n)
{
// Check (1 << i) bit is active or not
if ((arr(j) & (1 << i)) != 0)
{
// Change the status
isOdd = !isOdd;
}
if (isOdd == true)
{
// Increase counter position
oddBits += 1;
}
j += 1;
}
j = 0;
while (j < n)
{
// Change resultant sum
sum = sum + (multiplier * oddBits);
if ((arr(j) & (1 << i)) != 0)
{
oddBits = (n - j - oddBits);
}
j += 1;
}
// Reset odd counter indicator
isOdd = false;
oddBits = 0;
// Increase the multiplier by twice
multiplier = multiplier * 2;
i += 1;
}
// Display calculated result
print("XOR Sum : " + sum);
}
}
object Main
{
def main(args: Array[String]): Unit = {
var task: Subarray = new Subarray();
var arr: Array[Int] = Array(7, 2, 5, 1);
// Get the size of arr
var n: Int = arr.length;
/*
(7) + (2) + (5) + (1) +
(7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
(7^ 2^ 5) + (2^ 5 ^ 1) +
(7^ 2^ 5^ 1)
--------------
38
--------------
*/
task.sumSubarrayXor(arr, n);
}
}
input
XOR Sum : 38
import Foundation;
/*
Swift 4 Program for
Sum of XOR of all subarrays
*/
class Subarray
{
func sumSubarrayXor(_ arr: [Int], _ n: Int)
{
// Define some auxiliary variables
var sum = 0;
var multiplier = 1;
var oddBits = 0;
var isOdd = false;
var i = 0;
// Working on initial 30 bits
while (i < 30)
{
var j = 0;
// Count active bits in alternate elements
while (j < n)
{
// Check (1 << i) bit is active or not
if ((arr[j] & (1 << i)) != 0)
{
// Change the status
isOdd = !isOdd;
}
if (isOdd == true)
{
// Increase counter position
oddBits += 1;
}
j += 1;
}
j = 0;
while (j < n)
{
// Change resultant sum
sum = sum + (multiplier * oddBits);
if ((arr[j] & (1 << i)) != 0)
{
oddBits = (n - j - oddBits);
}
j += 1;
}
// Reset odd counter indicator
isOdd = false;
oddBits = 0;
// Increase the multiplier by twice
multiplier = multiplier * 2;
i += 1;
}
// Display calculated result
print("XOR Sum : ", sum, terminator: "");
}
}
func main()
{
let task = Subarray();
let arr = [7, 2, 5, 1];
// Get the size of arr
let n = arr.count;
/*
(7) + (2) + (5) + (1) +
(7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
(7^ 2^ 5) + (2^ 5 ^ 1) +
(7^ 2^ 5^ 1)
--------------
38
--------------
*/
task.sumSubarrayXor(arr, n);
}
main();
input
XOR Sum : 38
/*
Kotlin Program for
Sum of XOR of all subarrays
*/
class Subarray
{
fun sumSubarrayXor(arr: Array < Int > , n: Int): Unit
{
// Define some auxiliary variables
var sum: Int = 0;
var multiplier: Int = 1;
var oddBits: Int = 0;
var isOdd: Boolean = false;
var i: Int = 0;
// Working on initial 30 bits
while (i < 30)
{
var j: Int = 0;
// Count active bits in alternate elements
while (j < n)
{
// Check (1 << i) bit is active or not
if ((arr[j] and(1 shl i)) != 0)
{
// Change the status
isOdd = !isOdd;
}
if (isOdd == true)
{
// Increase counter position
oddBits += 1;
}
j += 1;
}
j = 0;
while (j < n)
{
// Change resultant sum
sum = sum + (multiplier * oddBits);
if ((arr[j] and(1 shl i)) != 0)
{
oddBits = (n - j - oddBits);
}
j += 1;
}
// Reset odd counter indicator
isOdd = false;
oddBits = 0;
// Increase the multiplier by twice
multiplier = multiplier * 2;
i += 1;
}
// Display calculated result
print("XOR Sum : " + sum);
}
}
fun main(args: Array < String > ): Unit
{
val task: Subarray = Subarray();
val arr: Array < Int > = arrayOf(7, 2, 5, 1);
// Get the size of arr
val n: Int = arr.count();
/*
(7) + (2) + (5) + (1) +
(7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
(7^ 2^ 5) + (2^ 5 ^ 1) +
(7^ 2^ 5^ 1)
--------------
38
--------------
*/
task.sumSubarrayXor(arr, n);
}
input
XOR Sum : 38
package main
import "fmt"
/*
Go Program for
Sum of XOR of all subarrays
*/
func sumSubarrayXor(arr[] int, n int) {
// Define some auxiliary variables
var sum int = 0
var multiplier int = 1
var oddBits int = 0
var isOdd bool = false
// Working on initial 30 bits
for i := 0 ; i < 30 ; i++ {
// Count active bits in alternate elements
for j := 0 ; j < n ; j++ {
// Check (1 << i) bit is active or not
if (arr[j] & (1 << i)) != 0 {
// Change the status
isOdd = !isOdd
}
if isOdd == true {
// Increase counter position
oddBits++
}
}
for j := 0 ; j < n ; j++ {
// Change resultant sum
sum = sum + (multiplier * oddBits)
if (arr[j] & (1 << i)) != 0 {
oddBits = (n - j - oddBits)
}
}
// Reset odd counter indicator
isOdd = false
oddBits = 0
// Increase the multiplier by twice
multiplier = multiplier * 2
}
// Display calculated result
fmt.Print("XOR Sum : ", sum)
}
func main() {
var arr = [] int {
7,
2,
5,
1,
}
// Get the size of arr
var n int = len(arr)
/*
(7) + (2) + (5) + (1) +
(7 ^ 2) + (2 ^ 5) + (5 ^ 1) +
(7^ 2^ 5) + (2^ 5 ^ 1) +
(7^ 2^ 5^ 1)
--------------
38
--------------
*/
sumSubarrayXor(arr, n)
}
input
XOR Sum : 38
Time Complexity
The time complexity of this algorithm is O(N * 30), which simplifies to O(N) since the inner loops run a constant number of times (30 times) regardless of the input size N.
Please share your knowledge to improve code and content standard. Also submit your doubts, and test case. We improve by your feedback. We will try to resolve your query as soon as possible.
New Comment