Given an array arr[] consisting of N non-negative integers, the task is to count the number of ways to split the array into three different non-empty subarrays such that Bitwise XOR of each subarray is equal.
Examples:
Input: arr[] = {7, 0, 5, 2, 7}
Output: 2
Explanation: All possible ways are:
{{7}, {0, 5, 2}, {7}} where XOR value of each subarray is 7
{{7, 0}, {5, 2}, {7}} where XOR value of each subarray is 7
Input: arr[] = {3, 1, 4}
Output: 0
Naive Approach: The simplest approach is to split the array into three non-empty subarrays using three loops and check whether the XOR of each subarray are equal or not. If the given condition holds true, then increase the final count. Print the final count obtained.
Time Complexity: O(N3)
Auxiliary Space: O(1)
Efficient Approach: The above approach can be optimized based on the following observations:
- Let xor_arr be the XOR of all elements of the array arr[].
- If arr[] can be split into three different subarrays of equal XOR values, then XOR of all elements in each subarray will be equal to xor_arr.
- So, the idea is to find all the prefix and suffix arrays with XOR value equal to xor_arr.
- If the total length of such a prefix and suffix array is less than N, then there exists another subarray between them with XOR value equal to xor_arr.
Hence, count the total number of all such prefix and suffix arrays that satisfy the above condition. Follow the steps below to solve the given problem:
- Store the XOR of all elements of the array, arr[] in a variable xor_arr.
- Create an array, pref_ind[] to store the ending points of every prefix array whose XOR value is equal to xor_arr.
- Traverse the array, arr[] and insert the ending points of every prefix array whose XOR value is equal to xor_arr in pref_ind.
- Create another array, suff_inds[] of size N where suff_inds[i] stores the total number of suffix arrays with XOR value equal to xor_arr whose starting point is greater than or equal to i.
- Traverse the array, arr[] in reverse order to fill the suff_inds[] array. If the current suffix array XOR value equals xor_arr, then increment suff_inds[i] by 1. Also, add the value of suff_inds[i+1] to suff_inds[i].
- For every element idx in pref_ind if the value of idx < N-1, then add the value of suff_inds[idx + 2] to the final count.
- Finally, print the value of the final count as the result.
Below is the implementation of the above approach:
C++
#include <bits/stdc++.h>
using namespace std;
int countWays( int arr[], int N)
{
int arr_xor = 0;
for ( int i = 0; i < N; i++)
arr_xor ^= arr[i];
int pref_xor = 0, suff_xor = 0;
vector< int > pref_ind;
int suff_inds[N + 1];
memset (suff_inds, 0, sizeof suff_inds);
for ( int i = 0; i < N; i++) {
pref_xor ^= arr[i];
if (pref_xor == arr_xor)
pref_ind.push_back(i);
}
for ( int i = N - 1; i >= 0; i--) {
suff_xor ^= arr[i];
suff_inds[i] += suff_inds[i + 1];
if (suff_xor == arr_xor)
suff_inds[i]++;
}
int tot_ways = 0;
for ( int idx : pref_ind) {
if (idx < N - 1)
tot_ways += suff_inds[idx + 2];
}
return tot_ways;
}
int main()
{
int arr[] = { 7, 0, 5, 2, 7 };
int N = sizeof (arr) / sizeof (arr[0]);
cout << countWays(arr, N);
return 0;
}
|
Java
import java.lang.*;
import java.util.*;
class GFG
{
static int countWays( int arr[], int N)
{
int arr_xor = 0 ;
for ( int i = 0 ; i < N; i++)
arr_xor ^= arr[i];
int pref_xor = 0 , suff_xor = 0 ;
ArrayList<Integer> pref_ind= new ArrayList<>();
int [] suff_inds= new int [N + 1 ];
for ( int i = 0 ; i < N; i++) {
pref_xor ^= arr[i];
if (pref_xor == arr_xor)
pref_ind.add(i);
}
for ( int i = N - 1 ; i >= 0 ; i--) {
suff_xor ^= arr[i];
suff_inds[i] += suff_inds[i + 1 ];
if (suff_xor == arr_xor)
suff_inds[i]++;
}
int tot_ways = 0 ;
for (Integer idx : pref_ind) {
if (idx < N - 1 )
tot_ways += suff_inds[idx + 2 ];
}
return tot_ways;
}
public static void main(String[] args)
{
int arr[] = { 7 , 0 , 5 , 2 , 7 };
int N = arr.length;
System.out.println(countWays(arr, N));
}
}
|
Python3
def countWays(arr, N):
arr_xor = 0
for i in range (N):
arr_xor ^ = arr[i]
pref_xor, suff_xor = 0 , 0
pref_ind = []
suff_inds = [ 0 ] * (N + 1 )
for i in range (N):
pref_xor ^ = arr[i]
if (pref_xor = = arr_xor):
pref_ind.append(i)
for i in range (N - 1 , - 1 , - 1 ):
suff_xor ^ = arr[i]
suff_inds[i] + = suff_inds[i + 1 ]
if (suff_xor = = arr_xor):
suff_inds[i] + = 1
tot_ways = 0
for idx in pref_ind:
if (idx < N - 1 ):
tot_ways + = suff_inds[idx + 2 ]
return tot_ways
if __name__ = = '__main__' :
arr = [ 7 , 0 , 5 , 2 , 7 ]
N = len (arr)
print (countWays(arr, N))
|
C#
using System;
using System.Collections.Generic;
class GFG {
static int countWays( int [] arr, int N)
{
int arr_xor = 0;
for ( int i = 0; i < N; i++)
arr_xor ^= arr[i];
int pref_xor = 0, suff_xor = 0;
List< int > pref_ind = new List< int >();
int [] suff_inds = new int [N + 1];
for ( int i = 0; i < N; i++) {
pref_xor ^= arr[i];
if (pref_xor == arr_xor)
pref_ind.Add(i);
}
for ( int i = N - 1; i >= 0; i--) {
suff_xor ^= arr[i];
suff_inds[i] += suff_inds[i + 1];
if (suff_xor == arr_xor)
suff_inds[i]++;
}
int tot_ways = 0;
foreach ( int idx in pref_ind)
{
if (idx < N - 1)
tot_ways += suff_inds[idx + 2];
}
return tot_ways;
}
public static void Main( string [] args)
{
int [] arr = { 7, 0, 5, 2, 7 };
int N = arr.Length;
Console.WriteLine(countWays(arr, N));
}
}
|
Javascript
<script>
function countWays(arr, N)
{
let arr_xor = 0;
for (let i = 0; i < N; i++)
arr_xor ^= arr[i];
let pref_xor = 0, suff_xor = 0;
let pref_ind = [];
let suff_inds = new Array(N + 1);
suff_inds.fill(0);
for (let i = 0; i < N; i++) {
pref_xor ^= arr[i];
if (pref_xor == arr_xor)
pref_ind.push(i);
}
for (let i = N - 1; i >= 0; i--) {
suff_xor ^= arr[i];
suff_inds[i] += suff_inds[i + 1];
if (suff_xor == arr_xor)
suff_inds[i]++;
}
let tot_ways = 0;
for (let idx of pref_ind) {
if (idx < N - 1)
tot_ways += suff_inds[idx + 2];
}
return tot_ways;
}
let arr = [ 7, 0, 5, 2, 7 ];
let N = arr.length;
document.write(countWays(arr, N));
</script>
|
Time Complexity: O(N)
Auxiliary Space: O(N)
Feeling lost in the world of random DSA topics, wasting time without progress? It's time for a change! Join our DSA course, where we'll guide you on an exciting journey to master DSA efficiently and on schedule.
Ready to dive in? Explore our Free Demo Content and join our DSA course, trusted by over 100,000 geeks!
Last Updated :
29 Jun, 2021
Like Article
Save Article