Related Articles

Minimize remaining array element by repeatedly replacing pairs by half of one more than their sum

• Last Updated : 23 Jun, 2021

Given an array arr[] containing a permutation of first N natural numbers. In one operation, remove a pair (X, Y) from the array and insert (X + Y + 1) / 2 into the array. The task is to find the smallest array element that can be left remaining in the array by performing the given operation exactly N – 1 times and the N – 1 pairs. If multiple solutions exist, then print any one of them.

Examples:

Input: arr[] = {1, 2, 3, 4}
Output: {2}, { (2, 4), (3, 3), (1, 3) }
Explanation:
Selecting a pair(arr[1], arr[3]) modifies the array arr[] = {1, 3, 3}
Selecting a pair(arr[1], arr[2]) modifies the array arr[] = {1, 3}
Selecting a pair(arr[0], arr[1]) modifies the array arr[] = {2}
Therefore, the smallest element left in array = {2} and the pairs that can be selected are {(2, 4), (3, 3), (1, 3)}.

Input: arr[] = {3, 2, 1}
Output: {2}, { (3, 2), (3, 1) }

Approach:The problem can be solved using Greedy technique. Follow the steps below to solve the problem:

• Initialize an array, say pairsArr[] to store all the pairs that can be selected by performing the given operations.
• Create a priority queue, say pq to store all the array elements in the priority queue.
• Traverse pq while count elements left in pq is greater than 1 and in each operation pop the top two elements(X, Y) of pq, store (X, Y) in pairsArr[] and insert an element having the value (X + Y + 1) / 2 in pq.
• Finally, print the value of the element left in pq and pairsArr[].

Below is the implementation of the above approach:

C++

 `// C++ program to implement``// the above approach` `#include ``using` `namespace` `std;` `// Function to print the smallest element left``// in the array and the pairs by given operation``void` `smallestNumberLeftInPQ(``int` `arr[], ``int` `N)``{` `    ``// Stores array elements and return``    ``// the minimum element of arr[] in O(1)``    ``priority_queue<``int``> pq;` `    ``// Stores all the pairs that can be``    ``// selected by the given operations``    ``vector > pairsArr;` `    ``// Traverse the array arr[]``    ``for` `(``int` `i = 0; i < N; i++) {``        ``pq.push(arr[i]);``    ``}` `    ``// Traverse pq while count of elements``    ``// left in pq greater than 1``    ``while` `(pq.size() > 1) {` `        ``// Stores top element of pq``        ``int` `X = pq.top();` `        ``// Pop top element of pq``        ``pq.pop();` `        ``// Stores top element of pq``        ``int` `Y = pq.top();` `        ``// Pop top element of pq``        ``pq.pop();` `        ``// Insert (X + Y + 1) / 2 in pq``        ``pq.push((X + Y + 1) / 2);` `        ``// Insert the pair  (X, Y)``        ``// in pairsArr[]``        ``pairsArr.push_back({ X, Y });``    ``}` `    ``// Print the element left in pq``    ``// by performing the given operations``    ``cout << ``"{"` `<< pq.top() << ``"}, "``;` `    ``// Stores count of elements``    ``// in pairsArr[]``    ``int` `sz = pairsArr.size();` `    ``// Print all the pairs that can``    ``// be selected in given operations``    ``for` `(``int` `i = 0; i < sz; i++) {` `        ``// If i is the first``        ``// index of pairsArr[]``        ``if` `(i == 0) {``            ``cout << ``"{ "``;``        ``}` `        ``// Print current pairs of pairsArr[]``        ``cout << ``"("` `<< pairsArr[i].first``             ``<< ``", "` `<< pairsArr[i].second << ``")"``;` `        ``// If i is not the last index``        ``// of pairsArr[]``        ``if` `(i != sz - 1) {``            ``cout << ``", "``;``        ``}` `        ``// If i is the last index``        ``// of pairsArr[]``        ``if` `(i == sz - 1) {``            ``cout << ``" }"``;``        ``}``    ``}``}` `// Driver Code``int` `main()``{``    ``int` `arr[] = { 3, 2, 1 };` `    ``int` `N = ``sizeof``(arr) / ``sizeof``(arr[0]);` `    ``smallestNumberLeftInPQ(arr, N);``}`

Java

 `// Java program to implement``// the above approach``import` `java.util.*;` `class` `GFG``{``    ``static` `class` `pair``    ``{``        ``int` `first, second;``        ``public` `pair(``int` `first, ``int` `second) ``        ``{``            ``this``.first = first;``            ``this``.second = second;``        ``}   ``    ``}` `// Function to print the smallest element left``// in the array and the pairs by given operation``static` `void` `smallestNumberLeftInPQ(``int` `arr[], ``int` `N)``{` `    ``// Stores array elements and return``    ``// the minimum element of arr[] in O(1)``    ``PriorityQueue pq = ``new` `PriorityQueue<>((x, y) ->``                                    ``Integer.compare(y, x));` `    ``// Stores all the pairs that can be``    ``// selected by the given operations``    ``Vector pairsArr = ``new` `Vector<>();` `    ``// Traverse the array arr[]``    ``for` `(``int` `i = ``0``; i < N; i++)``    ``{``        ``pq.add(arr[i]);``    ``}` `    ``// Traverse pq while count of elements``    ``// left in pq greater than 1``    ``while` `(pq.size() > ``1``) {` `        ``// Stores top element of pq``        ``int` `X = pq.peek();` `        ``// Pop top element of pq``        ``pq.remove();` `        ``// Stores top element of pq``        ``int` `Y = pq.peek();` `        ``// Pop top element of pq``        ``pq.remove();` `        ``// Insert (X + Y + 1) / 2 in pq``        ``pq.add((X + Y + ``1``) / ``2``);` `        ``// Insert the pair  (X, Y)``        ``// in pairsArr[]``        ``pairsArr.add(``new` `pair( X, Y ));``    ``}` `    ``// Print the element left in pq``    ``// by performing the given operations``    ``System.out.print(``"{"` `+  pq.peek()+ ``"}, "``);` `    ``// Stores count of elements``    ``// in pairsArr[]``    ``int` `sz = pairsArr.size();` `    ``// Print all the pairs that can``    ``// be selected in given operations``    ``for` `(``int` `i = ``0``; i < sz; i++) {` `        ``// If i is the first``        ``// index of pairsArr[]``        ``if` `(i == ``0``) {``            ``System.out.print(``"{ "``);``        ``}` `        ``// Print current pairs of pairsArr[]``        ``System.out.print(``"("` `+  pairsArr.get(i).first``            ``+ ``", "` `+  pairsArr.get(i).second+ ``")"``);` `        ``// If i is not the last index``        ``// of pairsArr[]``        ``if` `(i != sz - ``1``) {``            ``System.out.print(``", "``);``        ``}` `        ``// If i is the last index``        ``// of pairsArr[]``        ``if` `(i == sz - ``1``) {``            ``System.out.print(``" }"``);``        ``}``    ``}``}` `// Driver Code``public` `static` `void` `main(String[] args)``{``    ``int` `arr[] = { ``3``, ``2``, ``1` `};``    ``int` `N = arr.length;``    ``smallestNumberLeftInPQ(arr, N);``}``}` `// This code is contributed by 29AjayKumar`

Python3

 `# Python3 program to implement``# the above approach` `# Function to print smallest``# element left in the array``# and the pairs by given operation``def` `smallestNumberLeftInPQ(arr, N):` `    ``# Stores array elements and``    ``# return the minimum element``    ``# of arr[] in O(1)``    ``pq ``=` `[]` `    ``# Stores all the pairs that can``    ``# be selected by the given operations``    ``pairsArr ``=` `[]` `    ``# Traverse the array arr[]``    ``for` `i ``in` `range``(N):``        ``pq.append(arr[i])``    ``pq ``=` `sorted``(pq)` `    ``# Traverse pq while count of``    ``# elements left in pq greater``    ``# than 1``    ``while` `(``len``(pq) > ``1``):` `        ``# Stores top element of pq``        ``X ``=` `pq[``-``1``]``        ` `        ``del` `pq[``-``1``]` `        ``# Stores top element of pq``        ``Y ``=` `pq[``-``1``]` `        ``# Pop top element of pq``        ``del` `pq[``-``1``]` `        ``# Insert (X + Y + 1) / 2``        ``# in pq``        ``pq.append((X ``+` `Y ``+` `1``) ``/``/` `2``)` `        ``# Insert the pair  (X, Y)``        ``# in pairsArr[]``        ``pairsArr.append([X, Y])` `        ``pq ``=` `sorted``(pq)` `    ``# Print element left in pq``    ``# by performing the given``    ``# operations``    ``print``(``"{"``, pq[``-``1``], ``"}, "``,``          ``end ``=` `"")` `    ``# Stores count of elements``    ``# in pairsArr[]``    ``sz ``=` `len``(pairsArr)` `    ``# Print the pairs that can``    ``# be selected in given operations``    ``for` `i ``in` `range``(sz):` `        ``# If i is the first``        ``# index of pairsArr[]``        ``if` `(i ``=``=` `0``):``            ``print``(``"{ "``, end ``=` `"")` `        ``# Print pairs of pairsArr[]``        ``print``(``"("``, pairsArr[i][``0``], ``","``,``              ``pairsArr[i][``1``], ``")"``, end ``=` `"")` `        ``# If i is not the last index``        ``# of pairsArr[]``        ``if` `(i !``=` `sz ``-` `1``):``            ``print``(end ``=` `", "``)` `        ``# If i is the last index``        ``# of pairsArr[]``        ``if` `(i ``=``=` `sz ``-` `1``):``            ``print``(end ``=` `" }"``)` `# Driver Code``if` `__name__ ``=``=` `'__main__'``:``  ` `    ``arr ``=` `[``3``, ``2``, ``1``]``    ``N ``=` `len``(arr)``    ``smallestNumberLeftInPQ(arr, N)` `# This code is contributed by Mohit Kumar 29`

C#

 `// C# program to implement``// the above approach``using` `System;``using` `System.Collections.Generic;` `class` `GFG{``    ` `public` `class` `pair``{``    ``public` `int` `first, second;``    ` `    ``public` `pair(``int` `first, ``int` `second)``    ``{``        ``this``.first = first;``        ``this``.second = second;``    ``}``}` `// Function to print the smallest element left``// in the array and the pairs by given operation``static` `void` `smallestNumberLeftInPQ(``int``[] arr,``                                   ``int` `N)``{``    ` `    ``// Stores array elements and return``    ``// the minimum element of []arr in O(1)``    ``List<``int``> pq = ``new` `List<``int``>();``    ` `    ``// Stores all the pairs that can be``    ``// selected by the given operations``    ``List pairsArr = ``new` `List();` `    ``// Traverse the array []arr``    ``for``(``int` `i = 0; i < N; i++)``    ``{``        ``pq.Add(arr[i]);``    ``}``    ``pq.Sort();``    ``pq.Reverse();``    ` `    ``// Traverse pq while count of elements``    ``// left in pq greater than 1``    ``while` `(pq.Count > 1)``    ``{``        ` `        ``// Stores top element of pq``        ``int` `X = pq[0];` `        ``// Pop top element of pq``        ``pq.RemoveAt(0);` `        ``// Stores top element of pq``        ``int` `Y = pq[0];` `        ``// Pop top element of pq``        ``pq.RemoveAt(0);` `        ``// Insert (X + Y + 1) / 2 in pq``        ``pq.Add((X + Y + 1) / 2);``        ``pq.Sort();``        ``pq.Reverse();``        ` `        ``// Insert the pair  (X, Y)``        ``// in pairsArr[]``        ``pairsArr.Add(``new` `pair(X, Y));``    ``}` `    ``// Print the element left in pq``    ``// by performing the given operations``    ``Console.Write(``"{"` `+ pq[0] + ``"}, "``);` `    ``// Stores count of elements``    ``// in pairsArr[]``    ``int` `sz = pairsArr.Count;` `    ``// Print all the pairs that can``    ``// be selected in given operations``    ``for``(``int` `i = 0; i < sz; i++)``    ``{``        ` `        ``// If i is the first``        ``// index of pairsArr[]``        ``if` `(i == 0)``        ``{``            ``Console.Write(``"{ "``);``        ``}` `        ``// Print current pairs of pairsArr[]``        ``Console.Write(``"("` `+ pairsArr[i].first + ``", "` `+``                            ``pairsArr[i].second + ``")"``);` `        ``// If i is not the last index``        ``// of pairsArr[]``        ``if` `(i != sz - 1)``        ``{``            ``Console.Write(``", "``);``        ``}` `        ``// If i is the last index``        ``// of pairsArr[]``        ``if` `(i == sz - 1)``        ``{``            ``Console.Write(``" }"``);``        ``}``    ``}``}` `// Driver Code``public` `static` `void` `Main(String[] args)``{``    ``int``[] arr = { 3, 2, 1 };``    ``int` `N = arr.Length;``    ` `    ``smallestNumberLeftInPQ(arr, N);``}``}` `// This code is contributed by aashish1995`

Javascript

 ``
Output:
`{2}, { (3, 2), (3, 1) }`

Time Complexity: O(N * log(N))

Auxiliary Space: O(N)

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.

My Personal Notes arrow_drop_up