Minimize cost of operation to equalize tower heights - GeeksforGeeks

14 Mar, 2022
Given heights of n (n <=10000) towers as an array h[]; we need to bring every tower to same height by either adding or removing blocks in a tower. Every addition or removal operation costs a different value in a different tower. The objective is to minimize this cost.Examples:  
Input : Tower heights h[] = {1, 2, 3}
Costs of operations cost[] = {10, 100, 1000}
Output : 120
The heights can be equalized by either "Removing 
one block from 3 and adding one in 1" or "Adding
two blocks in 1 and adding one in 2". Since the 
cost of operation in tower 3 is 1000, the first
process would yield 1010 while the second one 
yields 120. Since the second process yields the
lowest cost of operation, it is the required 
output.

Input : h[] = {7,1,5 }; 
        cost[] = { 1, 1, 1 }; 
Output : 6
abs(7-5) + abs(1-5) + abs(5-5) = 6 (taking 5
as final height)

Input : h[] = {2, 4, 8}
        cost[] = {10, 100, 1000}
Output : 460
 
Naive Approach : A naive approach would be to find the cost of each and every possible operation set, and then find the minimum cost of operation. This would give O(n2) in the worst case.Best Approach : The best approach here seems to be Binary search. We store the minimum height & alter our resultant height by a factor of 2 in each step.  
C++
Java
Python3
C#
PHP
Javascript
// C++ program to minimize the cost of operation// to bring all towers to same height.#include <bits/stdc++.h>using namespace std; // Returns the cost of entire operation in bringing// the height of all towers to equal height eq_hlong int costOfOperation(int n, int h[], int cost[],                         int eq_h){    // Initialize initial cost to 0    long int c = 0;     // Adding cost for each tower    for (int i = 0; i < n; i++)        c += abs(h[i] - eq_h) * cost[i];     return c;} // Return the minimum possible cost of operation// to bring all the towers of different height// in height[0..n-1] to same height.long long int Bsearch(int n, int h[], int cost[]){    long int max_h = *max_element(h, h + n);    long int ans = LONG_MAX;     // Do binary search for minimum cost    long int high = 1 + max_h;    long int low = 0;    while (high > low) {        int mid = (low + high) >> 1;         // Cost below mid        long int bm = (mid > 0) ?                costOfOperation(n, h, cost, mid - 1) :                LONG_MAX;         // Cost at mid        long int m = costOfOperation(n, h, cost, mid);         // Cost above mid        long int am = costOfOperation(n, h, cost, mid + 1);          // ans should hold the minimum cost of operation        ans = min(ans, m);         // Search lower cost        if (bm <= m)            high = mid;         // Search higher cost        else if (am <= m)            low = mid + 1;         // If am > m and bm > m        // then ans is m        else            return m;    }     return ans;} // Driver codeint main(){    int h[] = { 1, 2, 3 };    int cost[] = { 10, 100, 1000 };    int n = sizeof(h)/sizeof(h[0]);    cout << Bsearch(n, h, cost);    return 0;}
// Java program to minimize the cost of operation// to bring all towers to same height.import java.util.Arrays;public class MinCostOp_Mintowerheight {     // Returns the cost of entire operation in bringing    // the height of all towers to equal height eq_h    static long costOfOperation(int n, int h[], int cost[],                                                int eq_h)    {        // Initialize initial cost to 0        long c = 0;              // Adding cost for each tower        for (int i = 0; i < n; i++)            c += Math.abs(h[i] - eq_h) * cost[i];              return c;    }          // Return the minimum possible cost of operation    // to bring all the towers of different height    // in height[0..n-1] to same height.    static long Bsearch(int n, int h[], int cost[])    {        int max_h =    Arrays.stream(h).max().getAsInt();        long ans = Long.MAX_VALUE;              // Do binary search for minimum cost        long high = 1 + max_h;        long low = 0;        while (high > low) {            int mid = (int) ((low + high) >> 1);                  // Cost below mid            long bm = (mid > 0) ?                    costOfOperation(n, h, cost, mid - 1) :                    Long.MAX_VALUE;                  // Cost at mid            long m = costOfOperation(n, h, cost, mid);                  // Cost above mid            long am = costOfOperation(n, h, cost, mid + 1);                  // Break if the answer becomes equal to            // minimum cost m            if (ans == m)                break;                  // ans should hold the minimum cost of operation            ans = Long.min(ans, m);                  // Search lower cost            if (bm <= m)                high = mid;                  // Search higher cost            else if (am <= m)               low = mid + 1;            // If am > m and bm > m           // then ans is m           else               return m;        }              return ans;    }          // Driver code    public static void main(String args[])    {        int h[] = { 1, 2, 3 };        int cost[] = { 10, 100, 1000 };        int n = h.length;        System.out.println(Bsearch(n, h, cost));    }}// This code is contributed by Sumit Ghosh
# Python 3 program to minimize the cost of# operation to bring all towers to same height.import sys # Returns the cost of entire operation in# bringing the height of all towers to# equal height eq_hdef costOfOperation(n, h,cost, eq_h):         # Initialize initial cost to 0    c = 0     # Adding cost for each tower    for i in range(0, n, 1):        c += abs(h[i] - eq_h) * cost[i]     return c # Return the minimum possible cost of# operation to bring all the towers of# different height in height[0..n-1]# to same height.def Bsearch(n, h, cost):    max_h = h[0]    for i in range(len(h)):        if(h[i] > max_h):            max_h = h[i]    ans = sys.maxsize     # Do binary search for minimum cost    high = 1 + max_h    low = 0    while (high > low):        mid = (low + high) >> 1         # Cost below mid        if(mid > 0):            bm = costOfOperation(n, h, cost, mid - 1)         else:            bm = sys.maxsize         # Cost at mid        m = costOfOperation(n, h, cost, mid)         # Cost above mid        am = costOfOperation(n, h, cost, mid + 1)         # Break if the answer becomes equal        # to minimum cost m        if (ans == m):            break         # ans should hold the minimum cost        # of operation        ans = min(ans, m)         # Search lower cost        if (bm <= m):            high = mid         # Search higher cost        else if(am <= m):            low = mid + 1         # If am > m and bm > m        # then ans is m        else :            return m;     return ans # Driver codeif __name__ == '__main__':    h = [1, 2, 3]    cost = [10, 100, 1000]    n = len(h)    print(Bsearch(n, h, cost))     # This code is contributed by# Sahil_shelangia
// C# program to minimize the// cost of operation to bring// all towers to same height.using System;using System.Linq; public class MinCostOp_Mintowerheight{     // Returns the cost of entire    // operation in bringing the height    // of all towers to equal height eq_h    static long costOfOperation(int n, int []h,                                int []cost, int eq_h)    {        // Initialize initial cost to 0        long c = 0;             // Adding cost for each tower        for (int i = 0; i < n; i++)            c += Math.Abs(h[i] - eq_h) * cost[i];             return c;    }         // Return the minimum possible    // cost of operation to bring    // all the towers of different height    // in height[0..n-1] to same height.    static long Bsearch(int n, int []h, int []cost)    {        int max_h = h.Max();        long ans = long.MaxValue;             // Do binary search for minimum cost        long high = 1 + max_h;        long low = 0;        while (high > low)        {            int mid = (int) ((low + high) >> 1);                 // Cost below mid            long bm = (mid > 0) ?                    costOfOperation(n, h, cost, mid - 1) :                    long.MaxValue;                 // Cost at mid            long m = costOfOperation(n, h, cost, mid);                 // Cost above mid            long am = costOfOperation(n, h, cost, mid + 1);                 // Break if the answer becomes            //  equal to minimum cost m            if (ans == m)                break;                 // ans should hold the minimum            // cost of operation            ans = Math.Min(ans, m);                 // Search lower cost            if (bm <= m)                high = mid;                 // Search higher cost            else if (am <= m)                low = mid + 1;              // If am > m and bm > m            // then ans is m            else                return m;        }             return ans;    }         // Driver code    public static void Main(String []args)    {        int []h = { 1, 2, 3 };        int []cost = { 10, 100, 1000 };        int n = h.Length;        Console.WriteLine(Bsearch(n, h, cost));    }} // This code contributed by Rajput-Ji
<?php// PHP program to minimize the cost// of operation to bring all towers// to same height. // Returns the cost of entire operation// in bringing the height of all towers// to equal height eq_hfunction costOfOperation($n, $h, $cost, $eq_h){    // Initialize initial cost to 0    $c = 0;     // Adding cost for each tower    for ($i = 0; $i < $n; $i++)        $c += abs($h[$i] - $eq_h) * $cost[$i];     return $c;} // Return the minimum possible cost of operation// to bring all the towers of different height// in height[0..n-1] to same height.function Bsearch($n, $h, $cost){    $max_h = max($h);    $ans = PHP_INT_MAX;     // Do binary search for minimum cost    $high = 1 + $max_h;    $low = 0;    while ($high > $low)    {        $mid = ($low + $high) >> 1;         // Cost below mid        $bm = ($mid > 0) ?               costOfOperation($n, $h, $cost, $mid - 1) :                                           PHP_INT_MAX;         // Cost at mid        $m = costOfOperation($n, $h, $cost, $mid);         // Cost above mid        $am = costOfOperation($n, $h, $cost, $mid + 1);         // Break if the answer becomes equal to        // minimum cost m        if ($ans == $m)            break;         // ans should hold the minimum        // cost of operation        $ans = min($ans, $m);         // Search lower cost        if ($bm <= $m)            $high = $mid;         // Search higher cost        else if ($am <= $m)            $low = $mid + 1;          // If am > m and bm > m        // then ans is m        else            return $m;    }     return $ans;} // Driver code$h = array( 1, 2, 3 );$cost = array( 10, 100, 1000 );$n = count($h);echo Bsearch($n, $h, $cost); // This code is contributed by mits?>
<script> // JavaScript program to minimize the cost// of operation to bring all towers// to same height. // Returns the cost of entire operation// in bringing the height of all towers// to equal height eq_hfunction costOfOperation(n, h, cost, eq_h){    // Initialize initial cost to 0    let c = 0;     // Adding cost for each tower    for (let i = 0; i < n; i++)        c += Math.abs(h[i] - eq_h) * cost[i];     return c;} // Return the minimum possible cost of operation// to bring all the towers of different height// in height[0..n-1] to same height.function Bsearch(n, h, cost){    let max_h = [...h].sort((a, b) => a - b)[h.length - 1];    let ans = Number.MAX_SAFE_INTEGER;     // Do binary search for minimum cost    let high = 1 + max_h;    let low = 0;    while (high > low)    {        let mid = (low + high) >> 1;         // Cost below mid        let bm = (mid > 0) ?            costOfOperation(n, h, cost, mid - 1) :                                        PHP_INT_MAX;         // Cost at mid        let m = costOfOperation(n, h, cost, mid);         // Cost above mid        let am = costOfOperation(n, h, cost, mid + 1);         // Break if the answer becomes equal to        // minimum cost m        if (ans == m)            break;         // ans should hold the minimum        // cost of operation        ans = Math.min(ans, m);         // Search lower cost        if (bm <= m)            high = mid;         // Search higher cost        else if (am <= m)            low = mid + 1;          // If am > m and bm > m        // then ans is m        else            return m;    }     return ans;} // Driver codelet h = new Array( 1, 2, 3 );let cost = new Array( 10, 100, 1000 );let n = h.length;document.write(Bsearch(n, h, cost)); // This code is contributed by gfgking </script>
120
 
This article is contributed by Raghav Jajodia. If you like GeeksforGeeks and would like to contribute, you can also write an article using write.geeksforgeeks.org or mail your article to review-team@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above. 
sahilshelangia
Rajput-Ji
Mithun Kumar
Avnishkumar1
gfgking
surinderdawra388
Binary Search
Arrays
Arrays
Binary Search
Writing code in comment?
Please use ide.geeksforgeeks.org,
generate link and share the link here.
Program for Bridge and Torch problem
Window Sliding Technique
Binary Tree (Array implementation)
Segment Tree | Set 1 (Sum of given range)
MSD( Most Significant Digit ) Radix Sort
Building Heap from Array
Maximum Subarray Sum using Divide and Conquer algorithm
Product of Array except itself
Find duplicates in O(n) time and O(1) extra space | Set 1