Skip to content
Related Articles

Related Articles

Improve Article
Save Article
Like Article

Minimize replacements with values up to K to make sum of two given arrays equal

  • Last Updated : 30 Jun, 2021

Given a positive integer K and two arrays A[] and B[] consisting of M and N positive integers from the range [1, K] respectively, the task is to minimize the count of replacements of array elements by values from the range [1, K] such that the sum of elements of both the arrays becomes equal. If it is impossible to make the sum equal, then print -1.

Examples:

Attention reader! Don’t stop learning now. Get hold of all the important DSA concepts with the DSA Self Paced Course at a student-friendly price and become industry ready.  To complete your preparation from learning a language to DS Algo and many more,  please refer Complete Interview Preparation Course.

In case you wish to attend live classes with experts, please refer DSA Live Classes for Working Professionals and Competitive Programming Live for Students.

Input: K = 6, A[] = {3, 4, 1}, B[] = {6, 6, 6}
Output: 2
Explanation:
One of the possible way is to replace elements of array B[] at indexes 0 and 1 with 1 in two moves. Therefore, the array B[] modifies to {1, 1, 6}.
Now, the sum of both the arrays is 8, which is equal.



Input: A[] = {4, 3, 2}, B[] = {2, 3, 3, 1}, K = 6, N = 4, M = 3
Output: 0

Approach: The given problem can be solved using Two-pointer technique. Follow the steps below to solve the problem:

  • Initialize 4 variables, say l1 = 0, r1 = M – 1, l2 = 0, r2 = N – 1, used to traverse the array.
  • Initialize a variable, say res, to store the count of minimum replacements required.
  • Sort both the given arrays in ascending order.
  • Find the difference of the sum of both arrays and store it in a variable, say diff.
  • Iterate until l1 ≤ r1 or l2 ≤ r2 and perform the following steps:
    • If diff = 0: Break out of the loop.
    • If diff exceeds 0: Take the maximum between (A[r1] – 1) and (K – B[l2]) and subtract it from the difference diff and then increment l2, if the value of (K – B[l2]) is greater. Otherwise, decrement r1 by one.
    • Otherwise, take the maximum between (B[r2] – 1) and (K – A[l1]) and add it to the difference diff, then increment l1, if (K – A[l1]) is greater. Otherwise, decrement the value of r2 by 1.
    • Increment the value of res by 1.
  • After completing the above steps, print the value of res as the minimum number of replacements of array elements required.

Below is the implementation of the above approach:

C++




#include <bits/stdc++.h>
using namespace std;
 
// Function to find minimum number
// of replacements required to make
// the sum of two arrays equal
int makeSumEqual(vector<int> a, vector<int> b,
                 int K, int M, int N)
{
 
  // Stores the sum of a[]
  int sum1 = 0;
 
  // Stores the sum of b[]
  int sum2 = 0;
 
  // Calculate sum of the array a[]
  for (int el : a)
    sum1 += el;
 
  // Calculate sum of the array b[]
  for (int el : b)
    sum2 += el;
 
  // Stores the difference
  // between a[] and b[]
  int diff = sum1 - sum2;
 
  // Left and Right pointer
  // to traverse the array a[]
  int l1 = 0, r1 = M - 1;
 
  // Left and Right pointer
  // to traverse the array b[]
  int l2 = 0, r2 = N - 1;
 
  // Stores the count of moves
  int res = 0;
 
  // Sort the arrays in
  // ascending order
  sort(a.begin(),a.end());
  sort(b.begin(),b.end());
 
  // Iterate while diff != 0 and
  // l1 <= r1 or l2 <= r2
  while (l1 <= r1 || l2 <= r2)
  {
    if (diff == 0)
    {
      break;
    }
 
    // If diff is greater than 0
    if (diff > 0)
    {
 
      // If all pointers are valid
      if (l2 <= r2 && l1 <= r1)
      {
 
        if (K - b[l2] < a[r1] - 1) {
 
          int sub = min(
            a[r1] - 1, diff);
          diff -= sub;
          a[r1] -= sub;
          r1--;
        }
        else {
 
          int sub = min(
            K - b[l2], diff);
          diff -= sub;
          b[l2] += sub;
          l2++;
        }
      }
 
      // Otherwise, if only pointers
      // of array a[] is valid
      else if (l1 <= r1) {
 
        int sub = min(
          a[r1] - 1, diff);
        diff -= sub;
        a[r1] -= sub;
        r1--;
      }
 
      // Otherwise
      else {
 
        int sub = min(
          K - b[l2], diff);
        diff -= sub;
        b[l2] += sub;
        l2++;
      }
    }
 
    // If diff is less than 0
    else {
 
      // If all pointers are valid
      if (l1 <= r1 && l2 <= r2) {
        if (K - a[l1]
            < b[r2] - 1) {
 
          int sub = min(
            b[r2] - 1,
            -1 * diff);
          diff += sub;
          b[r2] -= sub;
          r2--;
        }
 
        else {
 
          int sub = min(
            K - a[l1],
            -1 * diff);
          diff += sub;
          a[l1] -= sub;
          l1++;
        }
      }
 
      // Otherwise, if only pointers
      // of array a[] is valid
      else if (l2 <= r2) {
 
        int sub
          = min(
          b[r2] - 1,
          -1 * diff);
        diff += sub;
        b[r2] -= sub;
        r2--;
      }
 
      // Otherwise
      else {
 
        int sub = min(
          K - a[l1], diff);
        diff += sub;
        a[l1] += sub;
        l1++;
      }
    }
 
    // Increment count
    // of res by one
    res++;
  }
 
  // If diff is 0, then return res
  if (diff == 0)
    return res;
 
  // Otherwise, return -1
  else
    return -1;
}
 
// Driver Code
int main()
{
  vector<int> A = { 1, 4, 3 };
  vector<int> B = { 6, 6, 6 };
  int M = A.size();
  int N = B.size();
  int K = 6;
 
  cout << makeSumEqual(A, B, K,M, N);
 
  return 0;
}
 
// This code is contributed by mohit kumar 29.

Java




// Java program for the above approach
import java.util.*;
 
class GFG {
 
    // Function to find minimum number
    // of replacements required to make
    // the sum of two arrays equal
    public static int makeSumEqual(
        int[] a, int[] b, int K,
        int M, int N)
    {
        // Stores the sum of a[]
        int sum1 = 0;
 
        // Stores the sum of b[]
        int sum2 = 0;
 
        // Calculate sum of the array a[]
        for (int el : a)
            sum1 += el;
 
        // Calculate sum of the array b[]
        for (int el : b)
            sum2 += el;
 
        // Stores the difference
        // between a[] and b[]
        int diff = sum1 - sum2;
 
        // Left and Right pointer
        // to traverse the array a[]
        int l1 = 0, r1 = M - 1;
 
        // Left and Right pointer
        // to traverse the array b[]
        int l2 = 0, r2 = N - 1;
 
        // Stores the count of moves
        int res = 0;
 
        // Sort the arrays in
        // ascending order
        Arrays.sort(a);
        Arrays.sort(b);
 
        // Iterate while diff != 0 and
        // l1 <= r1 or l2 <= r2
        while (l1 <= r1 || l2 <= r2) {
            if (diff == 0) {
 
                break;
            }
 
            // If diff is greater than 0
            if (diff > 0) {
 
                // If all pointers are valid
                if (l2 <= r2 && l1 <= r1) {
 
                    if (K - b[l2] < a[r1] - 1) {
 
                        int sub = Math.min(
                            a[r1] - 1, diff);
                        diff -= sub;
                        a[r1] -= sub;
                        r1--;
                    }
                    else {
 
                        int sub = Math.min(
                            K - b[l2], diff);
                        diff -= sub;
                        b[l2] += sub;
                        l2++;
                    }
                }
 
                // Otherwise, if only pointers
                // of array a[] is valid
                else if (l1 <= r1) {
 
                    int sub = Math.min(
                        a[r1] - 1, diff);
                    diff -= sub;
                    a[r1] -= sub;
                    r1--;
                }
 
                // Otherwise
                else {
 
                    int sub = Math.min(
                        K - b[l2], diff);
                    diff -= sub;
                    b[l2] += sub;
                    l2++;
                }
            }
 
            // If diff is less than 0
            else {
 
                // If all pointers are valid
                if (l1 <= r1 && l2 <= r2) {
                    if (K - a[l1]
                        < b[r2] - 1) {
 
                        int sub = Math.min(
                            b[r2] - 1,
                            -1 * diff);
                        diff += sub;
                        b[r2] -= sub;
                        r2--;
                    }
 
                    else {
 
                        int sub = Math.min(
                            K - a[l1],
                            -1 * diff);
                        diff += sub;
                        a[l1] -= sub;
                        l1++;
                    }
                }
 
                // Otherwise, if only pointers
                // of array a[] is valid
                else if (l2 <= r2) {
 
                    int sub
                        = Math.min(
                            b[r2] - 1,
                            -1 * diff);
                    diff += sub;
                    b[r2] -= sub;
                    r2--;
                }
 
                // Otherwise
                else {
 
                    int sub = Math.min(
                        K - a[l1], diff);
                    diff += sub;
                    a[l1] += sub;
                    l1++;
                }
            }
 
            // Increment count
            // of res by one
            res++;
        }
 
        // If diff is 0, then return res
        if (diff == 0)
            return res;
 
        // Otherwise, return -1
        else
            return -1;
    }
 
    // Driver Code
    public static void main(String[] args)
    {
        int[] A = { 1, 4, 3 };
        int[] B = { 6, 6, 6 };
        int M = A.length;
        int N = B.length;
        int K = 6;
 
        System.out.println(
            makeSumEqual(A, B, K,
                         M, N));
    }
}

C#




// C# program to implement
// the above approach
using System;
 
public class GFG
{
   
    // Function to find minimum number
    // of replacements required to make
    // the sum of two arrays equal
    public static int makeSumEqual(
        int[] a, int[] b, int K,
        int M, int N)
    {
       
        // Stores the sum of a[]
        int sum1 = 0;
 
        // Stores the sum of b[]
        int sum2 = 0;
 
        // Calculate sum of the array a[]
        foreach (int el in a)
            sum1 += el;
 
        // Calculate sum of the array b[]
        foreach (int el in b)
            sum2 += el;
 
        // Stores the difference
        // between a[] and b[]
        int diff = sum1 - sum2;
 
        // Left and Right pointer
        // to traverse the array a[]
        int l1 = 0, r1 = M - 1;
 
        // Left and Right pointer
        // to traverse the array b[]
        int l2 = 0, r2 = N - 1;
 
        // Stores the count of moves
        int res = 0;
 
        // Sort the arrays in
        // ascending order
        Array.Sort(a);
        Array.Sort(b);
 
        // Iterate while diff != 0 and
        // l1 <= r1 or l2 <= r2
        while (l1 <= r1 || l2 <= r2) {
            if (diff == 0) {
 
                break;
            }
 
            // If diff is greater than 0
            if (diff > 0) {
 
                // If all pointers are valid
                if (l2 <= r2 && l1 <= r1) {
 
                    if (K - b[l2] < a[r1] - 1) {
 
                        int sub = Math.Min(
                            a[r1] - 1, diff);
                        diff -= sub;
                        a[r1] -= sub;
                        r1--;
                    }
                    else {
 
                        int sub = Math.Min(
                            K - b[l2], diff);
                        diff -= sub;
                        b[l2] += sub;
                        l2++;
                    }
                }
 
                // Otherwise, if only pointers
                // of array a[] is valid
                else if (l1 <= r1) {
 
                    int sub = Math.Min(
                        a[r1] - 1, diff);
                    diff -= sub;
                    a[r1] -= sub;
                    r1--;
                }
 
                // Otherwise
                else {
 
                    int sub = Math.Min(
                        K - b[l2], diff);
                    diff -= sub;
                    b[l2] += sub;
                    l2++;
                }
            }
 
            // If diff is less than 0
            else {
 
                // If all pointers are valid
                if (l1 <= r1 && l2 <= r2) {
                    if (K - a[l1]
                        < b[r2] - 1) {
 
                        int sub = Math.Min(
                            b[r2] - 1,
                            -1 * diff);
                        diff += sub;
                        b[r2] -= sub;
                        r2--;
                    }
 
                    else {
 
                        int sub = Math.Min(
                            K - a[l1],
                            -1 * diff);
                        diff += sub;
                        a[l1] -= sub;
                        l1++;
                    }
                }
 
                // Otherwise, if only pointers
                // of array a[] is valid
                else if (l2 <= r2) {
 
                    int sub
                        = Math.Min(
                            b[r2] - 1,
                            -1 * diff);
                    diff += sub;
                    b[r2] -= sub;
                    r2--;
                }
 
                // Otherwise
                else {
 
                    int sub = Math.Min(
                        K - a[l1], diff);
                    diff += sub;
                    a[l1] += sub;
                    l1++;
                }
            }
 
            // Increment count
            // of res by one
            res++;
        }
 
        // If diff is 0, then return res
        if (diff == 0)
            return res;
 
        // Otherwise, return -1
        else
            return -1;
    }
 
// Driver Code
public static void Main(String[] args)
{
    int[] A = { 1, 4, 3 };
        int[] B = { 6, 6, 6 };
        int M = A.Length;
        int N = B.Length;
        int K = 6;
 
        Console.WriteLine(
            makeSumEqual(A, B, K,
                         M, N));
}
}

Javascript




<script>
 
// Javascript program for the above approach
 
// Function to find minimum number
// of replacements required to make
// the sum of two arrays equal
function makeSumEqual(a,b,K,M,N)
{
        // Stores the sum of a[]
        let sum1 = 0;
  
        // Stores the sum of b[]
        let sum2 = 0;
  
        // Calculate sum of the array a[]
        for (let el=0;el< a.length;el++)
            sum1 += a[el];
  
        // Calculate sum of the array b[]
        for (let el=0;el< b.length;el++)
            sum2 += b[el];
  
        // Stores the difference
        // between a[] and b[]
        let diff = sum1 - sum2;
  
        // Left and Right pointer
        // to traverse the array a[]
        let l1 = 0, r1 = M - 1;
  
        // Left and Right pointer
        // to traverse the array b[]
        let l2 = 0, r2 = N - 1;
  
        // Stores the count of moves
        let res = 0;
  
        // Sort the arrays in
        // ascending order
        a.sort(function(c,d){return c-d;});
        b.sort(function(c,d){return c-d;});
  
        // Iterate while diff != 0 and
        // l1 <= r1 or l2 <= r2
        while (l1 <= r1 || l2 <= r2) {
            if (diff == 0) {
  
                break;
            }
  
            // If diff is greater than 0
            if (diff > 0) {
  
                // If all pointers are valid
                if (l2 <= r2 && l1 <= r1) {
  
                    if (K - b[l2] < a[r1] - 1) {
  
                        let sub = Math.min(
                            a[r1] - 1, diff);
                        diff -= sub;
                        a[r1] -= sub;
                        r1--;
                    }
                    else {
  
                        let sub = Math.min(
                            K - b[l2], diff);
                        diff -= sub;
                        b[l2] += sub;
                        l2++;
                    }
                }
  
                // Otherwise, if only pointers
                // of array a[] is valid
                else if (l1 <= r1) {
  
                    let sub = Math.min(
                        a[r1] - 1, diff);
                    diff -= sub;
                    a[r1] -= sub;
                    r1--;
                }
  
                // Otherwise
                else {
  
                    let sub = Math.min(
                        K - b[l2], diff);
                    diff -= sub;
                    b[l2] += sub;
                    l2++;
                }
            }
  
            // If diff is less than 0
            else {
  
                // If all pointers are valid
                if (l1 <= r1 && l2 <= r2) {
                    if (K - a[l1]
                        < b[r2] - 1) {
  
                        let sub = Math.min(
                            b[r2] - 1,
                            -1 * diff);
                        diff += sub;
                        b[r2] -= sub;
                        r2--;
                    }
  
                    else {
  
                        let sub = Math.min(
                            K - a[l1],
                            -1 * diff);
                        diff += sub;
                        a[l1] -= sub;
                        l1++;
                    }
                }
  
                // Otherwise, if only pointers
                // of array a[] is valid
                else if (l2 <= r2) {
  
                    let sub
                        = Math.min(
                            b[r2] - 1,
                            -1 * diff);
                    diff += sub;
                    b[r2] -= sub;
                    r2--;
                }
  
                // Otherwise
                else {
  
                    let sub = Math.min(
                        K - a[l1], diff);
                    diff += sub;
                    a[l1] += sub;
                    l1++;
                }
            }
  
            // Increment count
            // of res by one
            res++;
        }
  
        // If diff is 0, then return res
        if (diff == 0)
            return res;
  
        // Otherwise, return -1
        else
            return -1;
}
 
// Driver Code
let A=[1, 4, 3 ];
let B=[6, 6, 6 ];
let M = A.length;
let N = B.length;
let K = 6;
document.write(makeSumEqual(A, B, K,
                         M, N));
 
 
// This code is contributed by unknown2108
</script>
Output: 
2

 

Time Complexity: O(N)
Auxiliary Space: O(1)




My Personal Notes arrow_drop_up
Recommended Articles
Page :

Start Your Coding Journey Now!