Given two arrays A[] and B[] of equal sizes i.e. N containing integers from 1 to N. The task is to find sub-arrays from the given arrays such that they have equal sum. Print the indices of such sub-arrays. If no such sub-arrays are possible then print -1.
Examples:
Input: A[] = {1, 2, 3, 4, 5}, B[] = {6, 2, 1, 5, 4}
Output:
Indices in array 1 : 0, 1, 2
Indices in array 2 : 0
A[0..2] = 1 + 2 + 3 = 6
B[0] = 6Input: A[] = {10, 1}, B[] = {5, 3}
Output: -1
No such sub-arrays.
Approach: Let Ai denote the sum of first i elements in A and Bj denote the sum of first j elements in B. Without loss of generality we assume that An <= Bn.
Now Bn >= An >= Ai. So for each Ai we can find the smallest j such that Ai <= Bj. For each i we find the difference
Bj – Ai .
If difference is 0 then we are done as the elements from 1 to i in A and 1 to j in B have the same sum. Suppose difference is not 0.Then the difference must lie in the range [1, n-1].
Proof:
Let Bj – Ai >= n
Bj >= Ai + n
Bj-1 >= Ai (As the jth element in B can be at most n so Bj <= Bj-1 + n)
Now this is a contradiction as we had assumed that j is the smallest index
such that Bj >= Ai is j. So our assumption is wrong.
So Bj – Ai < n
Now there are n such differences(corresponding to each index) but only (n-1) possible values, so at least two indices will produce the same difference(By Pigeonhole principle). Let Aj – By = Ai – Bx. On rearranging we get Aj – Ai = By – Bx. So the required subarrays are [ i+1, j ] in A and [ x+1, y ] in B.
Below is the implementation of the above approach:
C++
// C++ implementation of the approach #include <bits/stdc++.h> using namespace std; // Function to print the valid indices in the array void printAns( int x, int y, int num) { cout << "Indices in array " << num << " : " ; for ( int i = x; i < y; ++i) { cout << i << ", " ; } cout << y << "\n" ; } // Function to find sub-arrays from two // different arrays with equal sum void findSubarray( int N, int a[], int b[], bool swap) { // Map to store the indices in A and B // which produce the given difference std::map< int , pair< int , int > > index; int difference; index[0] = make_pair(-1, -1); int j = 0; for ( int i = 0; i < N; ++i) { // Find the smallest j such that b[j] >= a[i] while (b[j] < a[i]) { j++; } difference = b[j] - a[i]; // Difference encountered for the second time if (index.find(difference) != index.end()) { // b[j] - a[i] = b[idx.second] - a[idx.first] // b[j] - b[idx.second] = a[i] = a[idx.first] // So sub-arrays are a[idx.first+1...i] and b[idx.second+1...j] if (swap) { pair< int , int > idx = index[b[j] - a[i]]; printAns(idx.second + 1, j, 1); printAns(idx.first + 1, i, 2); } else { pair< int , int > idx = index[b[j] - a[i]]; printAns(idx.first + 1, i, 1); printAns(idx.second + 1, j, 2); } return ; } // Store the indices for difference in the map index[difference] = make_pair(i, j); } cout << "-1" ; } // Utility function to calculate the // cumulative sum of the array void cumulativeSum( int arr[], int n) { for ( int i = 1; i < n; ++i) arr[i] += arr[i - 1]; } // Driver code int main() { int a[] = { 1, 2, 3, 4, 5 }; int b[] = { 6, 2, 1, 5, 4 }; int N = sizeof (a) / sizeof (a[0]); // Function to update the arrays // with their cumulative sum cumulativeSum(a, N); cumulativeSum(b, N); if (b[N - 1] > a[N - 1]) { findSubarray(N, a, b, false ); } else { // Swap is true as a and b are swapped during // function call findSubarray(N, b, a, true ); } return 0; } |
Python3
# Python3 implementation of the approach # Function to print the valid indices in the array def printAns(x, y, num): print ( "Indices in array" , num, ":" , end = " " ) for i in range (x, y): print (i, end = ", " ) print (y) # Function to find sub-arrays from two # different arrays with equal sum def findSubarray(N, a, b, swap): # Map to store the indices in A and B # which produce the given difference index = {} difference, j = 0 , 0 index[ 0 ] = ( - 1 , - 1 ) for i in range ( 0 , N): # Find the smallest j such that b[j] >= a[i] while b[j] < a[i]: j + = 1 difference = b[j] - a[i] # Difference encountered for the second time if difference in index: # b[j] - a[i] = b[idx.second] - a[idx.first] # b[j] - b[idx.second] = a[i] = a[idx.first] # So sub-arrays are a[idx.first+1...i] and b[idx.second+1...j] if swap: idx = index[b[j] - a[i]] printAns(idx[ 1 ] + 1 , j, 1 ) printAns(idx[ 0 ] + 1 , i, 2 ) else : idx = index[b[j] - a[i]] printAns(idx[ 0 ] + 1 , i, 1 ) printAns(idx[ 1 ] + 1 , j, 2 ) return # Store the indices for difference in the map index[difference] = (i, j) print ( "-1" ) # Utility function to calculate the # cumulative sum of the array def cumulativeSum(arr, n): for i in range ( 1 , n): arr[i] + = arr[i - 1 ] # Driver code if __name__ = = "__main__" : a = [ 1 , 2 , 3 , 4 , 5 ] b = [ 6 , 2 , 1 , 5 , 4 ] N = len (a) # Function to update the arrays # with their cumulative sum cumulativeSum(a, N) cumulativeSum(b, N) if b[N - 1 ] > a[N - 1 ]: findSubarray(N, a, b, False ) else : # Swap is true as a and b are # swapped during function call findSubarray(N, b, a, True ) # This code is contributed by Rituraj Jain |
Indices in array 1 : 0, 1, 2 Indices in array 2 : 0