Open In App

Minimum cost incurred before the geek reaches stone n

Improve
Improve
Like Article
Like
Save
Share
Report

Given n stones and array heights[] and Geek is standing at stone 1 and can jump to one of the following: Stone i+1, i+2, … i+k stone and cost will be [hi – hj] is incurred, where j is the stone to land on. Find the minimum possible total cost incurred before the Geek reaches Stone n.

Examples:

Input: n = 5, k = 3, heights[] = {10, 30, 40, 50, 20}
Output: 30
Explanation: Geek will follow the path 1->2->5, and the total cost would be | 10 – 30 | + | 30 – 20 | = 30, which is minimum

Input: n = 3, k = 1, heights[] = {10, 20, 10}
Output: 20
Explanation: Geek will follow the path 1->2->3, and the total cost would be |10 – 20 | + |20 – 10| = 20.

Approach: This can be solved with the following idea:

Using Dynamic Programming, we can calculate the minimum cost to travel n stones. At each i, we will look for the minimum value within k steps. 

Steps involved in the implementation of code:

  • Initializing dp vector.
  • Iterating for first k values for each index.
  • check if stones before this particular index are giving less cost or not.
  • If it is, update the dp for that particular index. 
  • if after traversing n > k is true.
  • Again iterate for k + 1 to n, following the same procedure.
  • Returning the dp[n – 1].

Below is the implementation of the above approach:

C++




// C++ code for the above approach:
#include <bits/stdc++.h>
#include <iostream>
using namespace std;
 
// Function to find minimum cost
// to travel n stones
void minCost(vector<int>& heights, int n, int k)
{
 
    // dp vector for having major of cost.
    vector<int> dp(n + 1);
 
    dp[0] = 0;
    dp[1] = abs(heights[0] - heights[1]);
 
    // For first k steps.
    for (int i = 2; i <= min(n, k); i++) {
        int x = INT_MAX;
        for (int j = 0; j < i; j++) {
 
            // Choosing minimum value
            if ((abs(heights[i] - heights[j]) + dp[j])
                < x) {
                x = abs(heights[i] - heights[j]) + dp[j];
            }
        }
        dp[i] = x;
    }
 
    // If n > k
    if (k < n) {
        for (int i = k + 1; i < n; i++) {
            int x = INT_MAX;
            for (int j = (i - k); j < i; j++) {
 
                // Choosing minimum value
                if ((abs(heights[i] - heights[j]) + dp[j])
                    < x) {
                    x = abs(heights[i] - heights[j])
                        + dp[j];
                }
            }
            dp[i] = x;
        }
    }
 
    // Finally we just cout
    // the minimum cost.
    cout << dp[n - 1] << endl;
}
 
// Driver code
int main()
{
 
    vector<int> heights = { 10, 30, 40, 50, 20 };
    int n = heights.size();
 
    // Max jump that we can take.
    int k = 3;
 
    // Function call
    minCost(heights, n, k);
 
    return 0;
}


Java




// Java code for the above approach:
 
import java.io.*;
 
class GFG {
 
    static void minCost(int[] heights, int n, int k)
    {
 
        // int[] for having major of cost.
        int[] dp = new int[n + 1];
 
        dp[0] = 0;
        dp[1] = Math.abs(heights[0] - heights[1]);
 
        // For first k steps.
        for (int i = 2; i <= Math.min(n, k); i++) {
            int x = Integer.MAX_VALUE;
            for (int j = 0; j < i; j++) {
 
                // Choosing minimum value
                if ((Math.abs(heights[i] - heights[j])
                     + dp[j])
                    < x) {
                    x = Math.abs(heights[i] - heights[j])
                        + dp[j];
                }
            }
            dp[i] = x;
        }
 
        // If n > k
        if (k < n) {
            for (int i = k + 1; i < n; i++) {
                int x = Integer.MAX_VALUE;
                for (int j = (i - k); j < i; j++) {
 
                    // Choosing minimum value
                    if ((Math.abs(heights[i] - heights[j])
                         + dp[j])
                        < x) {
                        x = Math.abs(heights[i]
                                     - heights[j])
                            + dp[j];
                    }
                }
                dp[i] = x;
            }
        }
 
        // Finally we just print the minimum cost.
        System.out.println(dp[n - 1]);
    }
 
    public static void main(String[] args)
    {
        int[] heights = { 10, 30, 40, 50, 20 };
        int n = heights.length;
 
        // Max jump that we can take
        int k = 3;
 
        // Function call
        minCost(heights, n, k);
    }
}
 
// This code is contributed by karthik.


Python3




# Python code for the above approach:
 
# Function to find minimum cost
# to travel n stones
 
 
def minCost(heights, n, k):
 
    # dp list for having major of cost.
    dp = [0] * (n + 1)
 
    dp[0] = 0
    dp[1] = abs(heights[0] - heights[1])
 
    # For first k steps.
    for i in range(2, min(n, k)+1):
        x = float('inf')
        for j in range(i):
 
            # Choosing minimum value
            if ((abs(heights[i] - heights[j]) + dp[j])
                    < x):
                x = abs(heights[i] - heights[j]) + dp[j]
        dp[i] = x
 
    # If n > k
    if (k < n):
        for i in range(k+1, n):
            x = float('inf')
            for j in range(i-k, i):
 
                # Choosing minimum value
                if ((abs(heights[i] - heights[j]) + dp[j])
                        < x):
                    x = abs(heights[i] - heights[j]) + dp[j]
            dp[i] = x
 
    # Finally we just print
    # the minimum cost.
    print(dp[n - 1])
 
 
# Driver code
heights = [10, 30, 40, 50, 20]
n = len(heights)
 
# Max jump that we can take.
k = 3
 
# Function call
minCost(heights, n, k)
 
# This code is contributed by prasad264


C#




using System;
using System.Collections.Generic;
 
public class Gfg {
    // Function to find minimum cost
    // to travel n stones
    static void minCost(List<int> heights, int n, int k) {
        // dp vector for having major of cost.
        List<int> dp = new List<int>(n + 1);
 
        dp.Add(0);
        dp.Add(Math.Abs(heights[0] - heights[1]));
 
        // For first k steps.
        for (int i = 2; i <= Math.Min(n, k); i++) {
            int x = int.MaxValue;
            for (int j = 0; j < i; j++) {
                // Choosing minimum value
                if ((Math.Abs(heights[i] - heights[j]) + dp[j]) < x) {
                    x = Math.Abs(heights[i] - heights[j]) + dp[j];
                }
            }
            dp.Add(x);
        }
 
        // If n > k
        if (k < n) {
            for (int i = k + 1; i < n; i++) {
                int x = int.MaxValue;
                for (int j = (i - k); j < i; j++) {
                    // Choosing minimum value
                    if ((Math.Abs(heights[i] - heights[j]) + dp[j]) < x) {
                        x = Math.Abs(heights[i] - heights[j]) + dp[j];
                    }
                }
                dp.Add(x);
            }
        }
 
        // Finally we just print the minimum cost.
        Console.WriteLine(dp[n - 1]);
    }
 
    // Driver code
    static void Main() {
        List<int> heights = new List<int> { 10, 30, 40, 50, 20 };
        int n = heights.Count;
 
        // Max jump that we can take.
        int k = 3;
 
        // Function call
        minCost(heights, n, k);
    }
}


Javascript




// JavaScript code for the above approach:
 
// Function to find minimum cost
// to travel n stones
function minCost(heights, n, k) {
 
    // dp array for storing the minimum cost
    let dp = new Array(n + 1);
     
    dp[0] = 0;
    dp[1] = Math.abs(heights[0] - heights[1]);
     
    // For first k steps.
    for (let i = 2; i <= Math.min(n, k); i++) {
        let x = Number.MAX_SAFE_INTEGER;
        for (let j = 0; j < i; j++) {
     
            // Choosing minimum value
            if ((Math.abs(heights[i] - heights[j]) + dp[j])
                < x) {
                x = Math.abs(heights[i] - heights[j]) + dp[j];
            }
        }
        dp[i] = x;
    }
     
    // If n > k
    if (k < n) {
        for (let i = k + 1; i < n; i++) {
            let x = Number.MAX_SAFE_INTEGER;
            for (let j = (i - k); j < i; j++) {
     
                // Choosing minimum value
                if ((Math.abs(heights[i] - heights[j]) + dp[j])
                    < x) {
                    x = Math.abs(heights[i] - heights[j])
                        + dp[j];
                }
            }
            dp[i] = x;
        }
    }
     
    // Finally we just print
    // the minimum cost.
    console.log(dp[n - 1]);
}
 
// Driver code
let heights = [10, 30, 40, 50, 20];
let n = heights.length;
 
// Max jump that we can take.
let k = 3;
 
// Function call
minCost(heights, n, k);


Output

30







Time Complexity: O(n*k)
Auxiliary Space: O(n+1)

Approach 2: Using the Hash Table

The hash table is used to store the minimum cost for each height reached, allowing for efficient retrieval and updating of costs during the iteration.

Steps involved in the implementation of code:

  • Initialize a hash table dp and setting the first and height and cost of zero.
  • Iterate over the heights from the second height to the last height.
  • Initialize a variable min_cost till the infinity.
  • Iterate over the previous heights and calculate the cost of getting to the current height from each of these previous heights. 
  • Update the min_cost to the minimum cost found in just above step.
  • Store the minimum cost in the hash table dp for the current value of height.
  • Return the minimum cost from the hash table for the last height.

Below is the implementation of the above approach:

C++




//C++ code for the above approach
#include <iostream>
#include <vector>
#include <unordered_map>
#include <cmath>
#include <limits>
 
using std::cout;
using std::endl;
using std::vector;
using std::unordered_map;
using std::min;
using std::abs;
using std::numeric_limits;
 
// Function to find minimum cost to travel n stones
int minCost(const vector<int>& heights, int n, int k) {
    // create a hash table to store the minimum cost to reach each stone
    unordered_map<int, int> dp;
 
    // cost of reaching the first stone is zero
    dp[heights[0]] = 0;
 
    // loop over the stones and calculate the minimum cost to reach each stone
    for (int i = 1; i < n; i++) {
        int min_cost = numeric_limits<int>::max();
 
        // loop over the previous k stones and find the minimum cost to reach the current stone
        for (int j = i-1; j >= std::max(0, i-k); j--) {
            int cost = dp[heights[j]] + abs(heights[i]-heights[j]);
            min_cost = min(min_cost, cost);
        }
 
        // store the minimum cost to reach the current stone in the hash table
        dp[heights[i]] = min_cost;
    }
 
    // return the minimum cost to reach the last stone
    return dp[heights[n-1]];
}
 
int main() {
    // input data
    vector<int> heights = { 10, 30, 40, 50, 20 };
    int n = heights.size();
    int k = 3;
 
    // calculate the minimum cost
    int cost = minCost(heights, n, k);
    cout << cost << endl;
 
    return 0;
}


Java




import java.util.HashMap;
import java.util.Map;
 
public class Main {
    // Function to find minimum cost to travel n stones
    public static int minCost(int[] heights, int n, int k) {
        // Create a hash table to store the minimum cost to reach each stone
        Map<Integer, Integer> dp = new HashMap<>();
 
        // Cost of reaching the first stone is zero
        dp.put(heights[0], 0);
 
        // Loop over the stones and calculate the minimum cost to reach each stone
        for (int i = 1; i < n; i++) {
            int minCost = Integer.MAX_VALUE;
 
            // Loop over the previous k stones and find the minimum cost to reach the current stone
            for (int j = i - 1; j >= Math.max(0, i - k); j--) {
                int cost = dp.get(heights[j]) + Math.abs(heights[i] - heights[j]);
                minCost = Math.min(minCost, cost);
            }
 
            // Store the minimum cost to reach the current stone in the hash table
            dp.put(heights[i], minCost);
        }
 
        // Return the minimum cost to reach the last stone
        return dp.get(heights[n - 1]);
    }
 
    public static void main(String[] args) {
        int[] heights = {10, 30, 40, 50, 20};
        int n = heights.length;
        int k = 3;
 
        // Calculate the minimum cost
        int cost = minCost(heights, n, k);
        System.out.println(cost);
    }
}


Python3




def min_cost(heights, k):
    # Create a dictionary to store the minimum cost to reach each stone
    dp = {}
 
    # Cost of reaching the first stone is zero
    dp[heights[0]] = 0
 
    # Loop over the stones and calculate the minimum cost to reach each stone
    for i in range(1, len(heights)):
        min_cost = float('inf')
 
        # Loop over the previous k stones and find the minimum cost to reach the current stone
        for j in range(i-1, max(0, i-k)-1, -1):
            cost = dp[heights[j]] + abs(heights[i] - heights[j])
            min_cost = min(min_cost, cost)
 
        # Store the minimum cost to reach the current stone in the dictionary
        dp[heights[i]] = min_cost
 
    # Return the minimum cost to reach the last stone
    return dp[heights[-1]]
 
# Main function
if __name__ == "__main__":
    # Input data
    heights = [10, 30, 40, 50, 20]
    k = 3
 
    # Calculate the minimum cost
    cost = min_cost(heights, k)
    print(cost)


C#




// C# Code for this approach
 
using System;
using System.Collections.Generic;
 
class Program
{
    // Function to find minimum cost to travel n stones
    public static int MinCost(int[] heights, int n, int k)
    {
        // Create a dictionary to store the minimum cost to reach each stone
        Dictionary<int, int> dp = new Dictionary<int, int>();
 
        // Cost of reaching the first stone is zero
        dp[heights[0]] = 0;
 
        // Loop over the stones and calculate the minimum cost to reach each stone
        for (int i = 1; i < n; i++)
        {
            int minCost = int.MaxValue;
 
            // Loop over the previous k stones and find the minimum
            // cost to reach the current stone
            for (int j = i - 1; j >= Math.Max(0, i - k); j--)
            {
                int cost = dp[heights[j]] + Math.Abs(heights[i] - heights[j]);
                minCost = Math.Min(minCost, cost);
            }
 
            // Store the minimum cost to reach the current stone in the dictionary
            dp[heights[i]] = minCost;
        }
 
        // Return the minimum cost to reach the last stone
        return dp[heights[n - 1]];
    }
 
    public static void Main(string[] args)
    {
        int[] heights = { 10, 30, 40, 50, 20 };
        int n = heights.Length;
        int k = 3;
 
        // Calculate the minimum cost
        int cost = MinCost(heights, n, k);
        Console.WriteLine(cost);
    }
}


Javascript




//JS code for the above approach
 
// Function to find minimum cost to travel n stones
function minCost( heights,  n,  k) {
    // create a hash table to store the minimum cost to reach each stone
    let dp=[];
 
    // cost of reaching the first stone is zero
    dp[heights[0]] = 0;
 
    // loop over the stones and calculate the minimum cost to reach each stone
    for (let i = 1; i < n; i++) {
        let min_cost = Number.MAX_VALUE;//numeric_limits<int>::max();
 
        // loop over the previous k stones and find the minimum cost to reach the current stone
        for (let j = i-1; j >= Math.max(0, i-k); j--) {
            let cost = dp[heights[j]] + Math.abs(heights[i]-heights[j]);
            min_cost = Math.min(min_cost, cost);
        }
 
        // store the minimum cost to reach the current stone in the hash table
        dp[heights[i]] = min_cost;
    }
 
    // return the minimum cost to reach the last stone
    return dp[heights[n-1]];
}
 
let heights = [ 10, 30, 40, 50, 20 ];
let n = heights.length;
let k = 3;
 
// calculate the minimum cost
let cost = minCost(heights, n, k);
console.log(cost);


Output:

30

Time Complexity: O(n*k), as we are computing the cost of reaching each stone from all previous stones that are within the maximum jump limit k.
Auxiliary Space: O(n), as we are using the hash table to store the minimum cost to reach at every stone.



Last Updated : 29 Oct, 2023
Like Article
Save Article
Previous
Next
Share your thoughts in the comments
Similar Reads