Given an array arr[] of rope lengths, connect all ropes into a single rope with the minimum total cost. The cost to connect two ropes is the sum of their lengths.
Examples:
Input: arr[] = [4, 3, 2, 6] Output: 29 Explanation: Minimum cost to connect all ropes into a single rope is Connect ropes 2 and 3 - [4, 5, 6], cost = 5 Connect ropes 4 and 5 - [9, 6], cost = 9 Connect ropes 9 and 6 - [15], cost = 15 Total cost = 5 + 9 + 15 = 29
[Naive Approach] Greedy with Repeated Sorting - O(n2*log(n)) Time and O(n) Space
The idea is to always connect the two shortest ropes first, minimizing the cost at each step using a greedy approach. We repeatedly sort the array, pick the two smallest ropes, connect them, and add their combined length back into the array while accumulating the cost. This process continues until only one rope remains.
C++
#include<iostream>#include<vector>#include<algorithm>usingnamespacestd;intminCost(vector<int>&arr){inttotalCost=0;// Continue until only one rope remainswhile(arr.size()>1){// Sort ropes to get the two smallest lengthssort(arr.begin(),arr.end());// Pick the two smallest ropesintfirst=arr[0];intsecond=arr[1];// Remove the two ropes from the arrayarr.erase(arr.begin());arr.erase(arr.begin());// Cost of connecting these two ropesintcost=first+second;totalCost+=cost;// Push the new rope back into the arrayarr.push_back(cost);}returntotalCost;}intmain(){vector<int>ropes={4,3,2,6};cout<<minCost(ropes)<<endl;return0;}
Java
importjava.util.Arrays;classGFG{staticintminCost(int[]arr){inttotalCost=0;intn=arr.length;// Continue until only one rope remainswhile(n>1){// Sort ropes to get the two smallest lengthsArrays.sort(arr,0,n);// Pick the two smallest ropesintfirst=arr[0];intsecond=arr[1];// Cost of connecting these two ropesintcost=first+second;totalCost+=cost;// Shift the array to remove the two smallest elementsfor(inti=2;i<n;i++){arr[i-2]=arr[i];}// Place the new rope at the endarr[n-2]=cost;// Reduce array size by 1 (two removed, one added)n--;}returntotalCost;}publicstaticvoidmain(String[]args){int[]ropes={4,3,2,6};System.out.println(minCost(ropes));}}
Python
defminCost(arr):totalCost=0# Continue until only one rope remainswhilelen(arr)>1:# Sort ropes to get the two smallest lengthsarr.sort()# Pick the two smallest ropesfirst=arr[0]second=arr[1]# Remove the two ropes from the arrayarr.pop(0)arr.pop(0)# Cost of connecting these two ropescost=first+secondtotalCost+=cost# Push the new rope back into the arrayarr.append(cost)returntotalCostif__name__=="__main__":ropes=[4,3,2,6]print(minCost(ropes))
C#
usingSystem;classGFG{staticintminCost(int[]arr){inttotalCost=0;intn=arr.Length;// Continue until only one rope remainswhile(n>1){// Sort ropes to get the two smallest lengthsArray.Sort(arr,0,n);// Pick the two smallest ropesintfirst=arr[0];intsecond=arr[1];// Cost of connecting these two ropesintcost=first+second;totalCost+=cost;// Shift the array to remove the two smallest elementsfor(inti=2;i<n;i++){arr[i-2]=arr[i];}// Place the new rope at the endarr[n-2]=cost;// Reduce array size by 1 (two removed, one added)n--;}returntotalCost;}staticvoidMain(){int[]ropes={4,3,2,6};Console.WriteLine(minCost(ropes));}}
JavaScript
functionminCost(arr){lettotalCost=0;// Continue until only one rope remainswhile(arr.length>1){// Sort ropes to get the two smallest lengthsarr.sort((a,b)=>a-b);// Pick the two smallest ropesletfirst=arr[0];letsecond=arr[1];// Remove the two ropes from the arrayarr.splice(0,2);// Cost of connecting these two ropesletcost=first+second;totalCost+=cost;// Push the new rope back into the arrayarr.push(cost);}returntotalCost;}functionmain(){letropes=[4,3,2,6];console.log(minCost(ropes));}main();
Output
29
[Expected Approach] Greedy with Heap - O(n*log(n)) Time and O(n) Space
Always connect the two smallest ropes first to minimize total cost, similar to Huffman coding.The idea is to use a min-heap(priority queue) and push all elements into it. While the heap contains more than one element, repeatedly extract the two smallest values, add them, and insert the sum back into the heap. Continue until one rope remains, then return the total cost.
C++
//Driver Code Starts#include<iostream>#include<vector>#include<queue>usingnamespacestd;//Driver Code EndsintminCost(vector<int>&arr){// Create a min priority queuepriority_queue<int,vector<int>,greater<int>>pq(arr.begin(),arr.end());// Initialize resultintres=0;// While size of priority queue is more than 1while(pq.size()>1){// Extract shortest two ropes from pqintfirst=pq.top();pq.pop();intsecond=pq.top();pq.pop();// Connect the ropes: update result and// insert the new rope to pqres+=first+second;pq.push(first+second);}returnres;}//Driver Code Startsintmain(){vector<int>arr={4,3,2,6};cout<<minCost(arr);return0;}//Driver Code Ends
Java
//Driver Code Startsimportjava.util.PriorityQueue;classGFG{//Driver Code EndsstaticintminCost(int[]arr){// Create a min priority queuePriorityQueue<Integer>pq=newPriorityQueue<>();for(intnum:arr){pq.add(num);}// Initialize resultintres=0;// While size of priority queue is more than 1while(pq.size()>1){// Extract shortest two ropes from pqintfirst=pq.poll();intsecond=pq.poll();// Connect the ropes: update result and// insert the new rope to pqres+=first+second;pq.add(first+second);}returnres;}//Driver Code Startspublicstaticvoidmain(String[]args){int[]arr={4,3,2,6};System.out.println(minCost(arr));}}//Driver Code Ends
Python
#Driver Code Startsimportheapq#Driver Code EndsdefminCost(arr):# Create a priority queue# By default, heapq provides a min-heapheapq.heapify(arr)# Initialize resultres=0# While size of priority queue is more than 1whilelen(arr)>1:# Extract shortest two ropes from pqfirst=heapq.heappop(arr)second=heapq.heappop(arr)# Connect the ropes: update result and# insert the new rope to pqres+=first+secondheapq.heappush(arr,first+second)returnres#Driver Code Startsif__name__=="__main__":arr=[4,3,2,6]print(minCost(arr))#Driver Code Ends
C#
//Driver Code StartsusingSystem;usingSystem.Collections.Generic;// Custom MinHeap classclassMinHeap{privateList<int>heap=newList<int>();privatevoidSwap(inti,intj){inttemp=heap[i];heap[i]=heap[j];heap[j]=temp;}publicvoidAdd(intval){heap.Add(val);inti=heap.Count-1;while(i>0){intparent=(i-1)/2;if(heap[i]>=heap[parent])break;Swap(i,parent);i=parent;}}publicintPop(){if(heap.Count==0)thrownewInvalidOperationException("Heap is empty");introot=heap[0];heap[0]=heap[heap.Count-1];heap.RemoveAt(heap.Count-1);inti=0;while(true){intleft=2*i+1;intright=2*i+2;intsmallest=i;if(left<heap.Count&&heap[left]<heap[smallest])smallest=left;if(right<heap.Count&&heap[right]<heap[smallest])smallest=right;if(smallest==i)break;Swap(i,smallest);i=smallest;}returnroot;}publicintCount(){returnheap.Count;}}classGFG{//Driver Code EndsstaticintminCost(int[]arr){// Create a min priority queueMinHeappq=newMinHeap();foreach(intvalinarr)pq.Add(val);// Initialize resultintres=0;// While size of priority queue is more than 1while(pq.Count()>1){// Extract shortest two ropes from pqintfirst=pq.Pop();intsecond=pq.Pop();// Connect the ropes: update result//and insert the new rope to pqres+=first+second;pq.Add(first+second);}returnres;}//Driver Code StartsstaticvoidMain(){int[]arr={4,3,2,6};Console.WriteLine(minCost(arr));}}//Driver Code Ends
JavaScript
//Driver Code StartsclassMinHeap{constructor(){this.heap=[];}// Insert a value into the heappush(val){this.heap.push(val);this.heapifyUp();}// Remove and return the smallest elementpop(){if(this.heap.length===1){returnthis.heap.pop();}constroot=this.heap[0];this.heap[0]=this.heap.pop();this.heapifyDown();returnroot;}// Return the smallest element without removing ittop(){returnthis.heap[0];}// Return the size of the heapsize(){returnthis.heap.length;}// Restore the heap property upwardsheapifyUp(){letindex=this.heap.length-1;while(index>0){constparentIndex=Math.floor((index-1)/2);if(this.heap[index]>=this.heap[parentIndex]){break;}[this.heap[index],this.heap[parentIndex]]=[this.heap[parentIndex],this.heap[index]];index=parentIndex;}}// Restore the heap property downwardsheapifyDown(){letindex=0;constsize=this.heap.length;while(true){constleftChild=2*index+1;constrightChild=2*index+2;letsmallest=index;if(leftChild<size&&this.heap[leftChild]<this.heap[smallest]){smallest=leftChild;}if(rightChild<size&&this.heap[rightChild]<this.heap[smallest]){smallest=rightChild;}if(smallest===index){break;}[this.heap[index],this.heap[smallest]]=[this.heap[smallest],this.heap[index]];index=smallest;}}}//Driver Code EndsfunctionminCost(arr){// Create a min-heap constpq=newMinHeap();arr.forEach(num=>pq.push(num));// Initialize resultletres=0;// While size of priority queue is more than 1while(pq.size()>1){// Extract shortest two ropes from pqconstfirst=pq.pop();constsecond=pq.pop();// Connect the ropes: update result and// insert the new rope to pqres+=first+second;pq.push(first+second);}returnres;}//Driver Code Starts// Driver Code constarr=[4,3,2,6];console.log(minCost(arr));//Driver Code Ends